Repository: kindahl/infrarecorder Branch: master Commit: ec170530151c Files: 518 Total size: 3.1 MB Directory structure: gitextract_4e0u9_x1/ ├── .gitignore ├── dep/ │ └── readme.txt ├── doc/ │ ├── english/ │ │ ├── help_english_vc08.vcproj │ │ ├── help_english_vc10.vcxproj │ │ ├── help_english_vc10.vcxproj.filters │ │ ├── how_to_use/ │ │ │ ├── burn_image.html │ │ │ ├── burn_options.html │ │ │ ├── configuration.html │ │ │ ├── copy_audio_disc.html │ │ │ ├── copy_data_disc.html │ │ │ ├── device_configuration.html │ │ │ ├── disc_information.html │ │ │ ├── erase_disc.html │ │ │ ├── fixate_disc.html │ │ │ ├── manage_tracks.html │ │ │ ├── read_options.html │ │ │ └── working_with_projects/ │ │ │ ├── add_boot_image.html │ │ │ ├── getting_started.html │ │ │ ├── multisession_disc.html │ │ │ └── project_settings.html │ │ ├── infra_recorder/ │ │ │ ├── acknowledgments.html │ │ │ ├── copyright.html │ │ │ ├── faq.html │ │ │ ├── feature_overview.html │ │ │ ├── installation.html │ │ │ ├── introduction.html │ │ │ ├── license_agreement.html │ │ │ ├── quick_start.html │ │ │ ├── system_requirements.html │ │ │ └── whats_new.html │ │ ├── infrarecorder.hhc │ │ ├── infrarecorder.hhk │ │ ├── infrarecorder.hhp │ │ ├── style.css │ │ └── stylescript.js │ └── french/ │ ├── French.chm │ ├── Gpl-3.0-FR.txt │ ├── InfraRecorder.hhp │ ├── InfraRecorderFR.hhc │ ├── InfraRecorderFR.hhk │ ├── fr.stp │ ├── how_to_use/ │ │ ├── burn_image.html │ │ ├── burn_options.html │ │ ├── configuration.html │ │ ├── copy_audio_disc.html │ │ ├── copy_data_disc.html │ │ ├── device_configuration.html │ │ ├── disc_information.html │ │ ├── erase_disc.html │ │ ├── fixate_disc.html │ │ ├── manage_tracks.html │ │ ├── read_options.html │ │ └── working_with_projects/ │ │ ├── add_boot_image.html │ │ ├── getting_started.html │ │ ├── multisession_disc.html │ │ └── project_settings.html │ ├── infra_recorder/ │ │ ├── acknowledgments.html │ │ ├── copyright.html │ │ ├── faq.html │ │ ├── feature_overview.html │ │ ├── installation.html │ │ ├── introduction.html │ │ ├── license_agreement.html │ │ ├── license_agreement_fr.html │ │ ├── quick_start.html │ │ ├── system_requirements.html │ │ └── whats_new.html │ ├── style.css │ └── stylescript.js ├── etc/ │ ├── codecs/ │ │ └── readme.txt │ └── translations/ │ ├── help/ │ │ ├── czech.chm │ │ ├── french.chm │ │ ├── german.chm │ │ ├── russian.chm │ │ ├── thai.chm │ │ ├── turkish.chm │ │ └── ukrainian.chm │ ├── install.txt │ ├── readme.txt │ └── software/ │ ├── albanian.irl │ ├── arabic.irl │ ├── armenian.irl │ ├── basque.irl │ ├── bosnian.irl │ ├── bulgarian.irl │ ├── catalan.irl │ ├── chinese-simplified.irl │ ├── chinese-traditional.irl │ ├── chuvash.irl │ ├── croatian.irl │ ├── czech.irl │ ├── danish.irl │ ├── dutch.irl │ ├── english.irl │ ├── estonian.irl │ ├── farsi.irl │ ├── finnish.irl │ ├── french.irl │ ├── galician.irl │ ├── georgian.irl │ ├── german.irl │ ├── greek.irl │ ├── hebrew.irl │ ├── hungarian.irl │ ├── indonesian.irl │ ├── italian.irl │ ├── japanese.irl │ ├── korean.irl │ ├── latvian.irl │ ├── lithuanian.irl │ ├── macedonian.irl │ ├── norwegian.irl │ ├── polish.irl │ ├── portuguese-brazilian.irl │ ├── portuguese.irl │ ├── romanian.irl │ ├── russian.irl │ ├── serbian-cyrillic.irl │ ├── serbian-latin.irl │ ├── slovak.irl │ ├── slovenian.irl │ ├── spanish.irl │ ├── swedish.irl │ ├── thai.irl │ ├── turkish.irl │ ├── ukrainian.irl │ ├── valencian.irl │ └── vietnamese.irl ├── license.rtf ├── license.txt ├── makelinks.bat ├── readme.txt ├── sign.bat └── src/ ├── app/ │ ├── action_manager.cc │ ├── action_manager.hh │ ├── advanced_progress.cc │ ├── advanced_progress.hh │ ├── atl_compat.hh │ ├── control/ │ │ ├── custom_button.cc │ │ ├── custom_button.hh │ │ ├── custom_combo_box.cc │ │ ├── custom_combo_box.hh │ │ ├── custom_container.cc │ │ ├── custom_container.hh │ │ ├── custom_edit_ctrl.cc │ │ ├── custom_edit_ctrl.hh │ │ ├── custom_header_ctrl.cc │ │ ├── custom_header_ctrl.hh │ │ ├── custom_multi_button.cc │ │ ├── custom_multi_button.hh │ │ ├── custom_toolbar_ctrl.cc │ │ ├── custom_toolbar_ctrl.hh │ │ ├── double_buffered_static.cc │ │ ├── double_buffered_static.hh │ │ ├── drop_down_button.cc │ │ ├── drop_down_button.hh │ │ ├── gradient_static.cc │ │ ├── gradient_static.hh │ │ ├── label_container.cc │ │ ├── label_container.hh │ │ ├── mini_html_ctrl.cc │ │ ├── mini_html_ctrl.hh │ │ ├── project_list_view_ctrl.cc │ │ ├── project_list_view_ctrl.hh │ │ ├── project_tree_view_ctrl.cc │ │ ├── project_tree_view_ctrl.hh │ │ ├── shell_list_view_ctrl.cc │ │ ├── shell_list_view_ctrl.hh │ │ ├── space_meter.cc │ │ ├── space_meter.hh │ │ ├── title_tip_list_view_ctrl.cc │ │ ├── title_tip_list_view_ctrl.hh │ │ ├── welcome_pane.cc │ │ └── welcome_pane.hh │ ├── core/ │ │ ├── cd_text.cc │ │ ├── cd_text.hh │ │ ├── cdrtools_parse_strings.hh │ │ ├── core.cc │ │ ├── core.hh │ │ ├── core2.cc │ │ ├── core2.hh │ │ ├── core2_blank.cc │ │ ├── core2_blank.hh │ │ ├── core2_format.cc │ │ ├── core2_format.hh │ │ ├── core2_info.cc │ │ ├── core2_info.hh │ │ ├── core2_read.cc │ │ ├── core2_read.hh │ │ ├── core2_stream.cc │ │ ├── core2_stream.hh │ │ ├── core2_util.cc │ │ ├── core2_util.hh │ │ ├── diagnostics.cc │ │ ├── diagnostics.hh │ │ ├── scsi.cc │ │ └── scsi.hh │ ├── ctrl_messages.hh │ ├── dialog/ │ │ ├── about_window.cc │ │ ├── about_window.hh │ │ ├── add_boot_image_dlg.cc │ │ ├── add_boot_image_dlg.hh │ │ ├── burn_advanced_page.cc │ │ ├── burn_advanced_page.hh │ │ ├── burn_image_dlg.cc │ │ ├── burn_image_dlg.hh │ │ ├── burn_image_general_page.cc │ │ ├── burn_image_general_page.hh │ │ ├── config_advanced_page.cc │ │ ├── config_advanced_page.hh │ │ ├── config_dlg.cc │ │ ├── config_dlg.hh │ │ ├── config_general_page.cc │ │ ├── config_general_page.hh │ │ ├── config_language_page.cc │ │ ├── config_language_page.hh │ │ ├── config_shell_ext_page.cc │ │ ├── config_shell_ext_page.hh │ │ ├── confirm_file_replace_dlg.cc │ │ ├── confirm_file_replace_dlg.hh │ │ ├── copy_disc_dlg.cc │ │ ├── copy_disc_dlg.hh │ │ ├── copy_disc_general_page.cc │ │ ├── copy_disc_general_page.hh │ │ ├── copy_image_dlg.cc │ │ ├── copy_image_dlg.hh │ │ ├── copy_image_general_page.cc │ │ ├── copy_image_general_page.hh │ │ ├── device_advanced_page.cc │ │ ├── device_advanced_page.hh │ │ ├── device_dlg.cc │ │ ├── device_dlg.hh │ │ ├── device_general_page.cc │ │ ├── device_general_page.hh │ │ ├── devices_dlg.cc │ │ ├── devices_dlg.hh │ │ ├── disc_dlg.cc │ │ ├── disc_dlg.hh │ │ ├── disc_general_page.cc │ │ ├── disc_general_page.hh │ │ ├── edit_track_dlg.cc │ │ ├── edit_track_dlg.hh │ │ ├── erase_dlg.cc │ │ ├── erase_dlg.hh │ │ ├── fixate_dlg.cc │ │ ├── fixate_dlg.hh │ │ ├── import_session_dlg.cc │ │ ├── import_session_dlg.hh │ │ ├── info_dlg.cc │ │ ├── info_dlg.hh │ │ ├── log_dlg.cc │ │ ├── log_dlg.hh │ │ ├── main_frm.cc │ │ ├── main_frm.hh │ │ ├── main_view.cc │ │ ├── main_view.hh │ │ ├── new_file_ext_dlg.cc │ │ ├── new_file_ext_dlg.hh │ │ ├── progress_dlg.cc │ │ ├── progress_dlg.hh │ │ ├── project_prop_audio_page.cc │ │ ├── project_prop_audio_page.hh │ │ ├── project_prop_boot_page.cc │ │ ├── project_prop_boot_page.hh │ │ ├── project_prop_dlg.cc │ │ ├── project_prop_dlg.hh │ │ ├── project_prop_fields_page.cc │ │ ├── project_prop_fields_page.hh │ │ ├── project_prop_file_sys_page.cc │ │ ├── project_prop_file_sys_page.hh │ │ ├── project_prop_general_page.cc │ │ ├── project_prop_general_page.hh │ │ ├── project_prop_iso_page.cc │ │ ├── project_prop_iso_page.hh │ │ ├── project_prop_udf_page.cc │ │ ├── project_prop_udf_page.hh │ │ ├── read_options_page.cc │ │ ├── read_options_page.hh │ │ ├── save_tracks_dlg.cc │ │ ├── save_tracks_dlg.hh │ │ ├── simple_progress_dlg.cc │ │ ├── simple_progress_dlg.hh │ │ ├── splash_window.cc │ │ ├── splash_window.hh │ │ ├── tracks_dlg.cc │ │ ├── tracks_dlg.hh │ │ ├── wait_dlg.cc │ │ └── wait_dlg.hh │ ├── directory_monitor.cc │ ├── directory_monitor.hh │ ├── effects.cc │ ├── effects.hh │ ├── enum_fmt_etc.cc │ ├── enum_fmt_etc.hh │ ├── files_data_object.cc │ ├── files_data_object.hh │ ├── infrarecorder.cc │ ├── infrarecorder.hh │ ├── infrarecorder.rc │ ├── infrarecorder_vc08.vcproj │ ├── infrarecorder_vc10.vcxproj │ ├── infrarecorder_vc10.vcxproj.filters │ ├── pidl_helper.cc │ ├── pidl_helper.hh │ ├── png_file.cc │ ├── png_file.hh │ ├── project_data_object.cc │ ├── project_data_object.hh │ ├── project_drop_source.cc │ ├── project_drop_source.hh │ ├── project_drop_target_base.cc │ ├── project_drop_target_base.hh │ ├── project_manager.cc │ ├── project_manager.hh │ ├── registry.cc │ ├── registry.hh │ ├── resource.h │ ├── settings.cc │ ├── settings.hh │ ├── settings_manager.cc │ ├── settings_manager.hh │ ├── stdafx.cc │ ├── stdafx.hh │ ├── string_table.cc │ ├── string_table.hh │ ├── temp_manager.cc │ ├── temp_manager.hh │ ├── toolbar_manager.cc │ ├── toolbar_manager.hh │ ├── translated_strings.hh │ ├── tree_manager.cc │ ├── tree_manager.hh │ ├── utility/ │ │ ├── audio_util.cc │ │ ├── audio_util.hh │ │ ├── device_util.cc │ │ ├── device_util.hh │ │ ├── lang_util.cc │ │ ├── lang_util.hh │ │ ├── shell_ext_util.cc │ │ ├── shell_ext_util.hh │ │ ├── trans_util.cc │ │ └── trans_util.hh │ ├── version.cc │ ├── version.hh │ ├── visual_styles.cc │ └── visual_styles.hh ├── base/ │ ├── base_vc08.vcproj │ ├── base_vc10.vcxproj │ ├── base_vc10.vcxproj.filters │ ├── check_fmt_str_placeholders.cc │ ├── check_fmt_str_placeholders.hh │ ├── codec_const.hh │ ├── codec_manager.cc │ ├── codec_manager.hh │ ├── custom_string.hh │ ├── file_util.cc │ ├── file_util.hh │ ├── graph_util.cc │ ├── graph_util.hh │ ├── lng_processor.cc │ ├── lng_processor.hh │ ├── string_container.cc │ ├── string_container.hh │ ├── string_conv.cc │ ├── string_conv.hh │ ├── string_util.cc │ ├── string_util.hh │ ├── xml_processor.cc │ └── xml_processor.hh ├── codecs/ │ ├── lame/ │ │ ├── config_dlg.cc │ │ ├── config_dlg.hh │ │ ├── config_general_page.cc │ │ ├── config_general_page.hh │ │ ├── lame.cc │ │ ├── lame.def │ │ ├── lame.rc │ │ ├── lame_base.cc │ │ ├── lame_base.hh │ │ ├── lame_encoder.cc │ │ ├── lame_encoder.hh │ │ ├── lame_vc08.vcproj │ │ ├── lame_vc10.vcxproj │ │ ├── lame_vc10.vcxproj.filters │ │ ├── resource.h │ │ ├── stdafx.cc │ │ └── stdafx.hh │ ├── sndfile/ │ │ ├── library_helper.cc │ │ ├── library_helper.hh │ │ ├── sndfile.cc │ │ ├── sndfile.def │ │ ├── sndfile_vc08.vcproj │ │ ├── sndfile_vc10.vcxproj │ │ ├── sndfile_vc10.vcxproj.filters │ │ ├── stdafx.cc │ │ └── stdafx.hh │ ├── vorbis/ │ │ ├── config_dlg.cc │ │ ├── config_dlg.hh │ │ ├── config_general_page.cc │ │ ├── config_general_page.hh │ │ ├── resource.h │ │ ├── stdafx.cc │ │ ├── stdafx.hh │ │ ├── vorbis.cc │ │ ├── vorbis.def │ │ ├── vorbis.hh │ │ ├── vorbis.rc │ │ ├── vorbis_vc08.vcproj │ │ ├── vorbis_vc10.vcxproj │ │ └── vorbis_vc10.vcxproj.filters │ ├── wave/ │ │ ├── stdafx.cc │ │ ├── stdafx.hh │ │ ├── wave.cc │ │ ├── wave.def │ │ ├── wave_vc08.vcproj │ │ ├── wave_vc10.vcxproj │ │ ├── wave_vc10.vcxproj.filters │ │ ├── wave_writer.cc │ │ └── wave_writer.hh │ └── wma/ │ ├── config_dlg.cc │ ├── config_dlg.hh │ ├── config_general_page.cc │ ├── config_general_page.hh │ ├── library_helper.cc │ ├── library_helper.hh │ ├── read_stream.cc │ ├── read_stream.hh │ ├── resource.h │ ├── stdafx.cc │ ├── stdafx.hh │ ├── wma.cc │ ├── wma.def │ ├── wma.rc │ ├── wma_reader.cc │ ├── wma_reader.hh │ ├── wma_vc08.vcproj │ ├── wma_vc10.vcxproj │ └── wma_vc10.vcxproj.filters ├── infrarecorder_vc08.sln ├── infrarecorder_vc10.sln ├── setup/ │ ├── ir_plugin/ │ │ ├── ir_plugin.cc │ │ ├── ir_plugin.def │ │ ├── ir_plugin_vc08.vcproj │ │ ├── ir_plugin_vc10.vcxproj │ │ ├── ir_plugin_vc10.vcxproj.filters │ │ ├── settings.cc │ │ ├── settings.hh │ │ ├── stdafx.cc │ │ └── stdafx.hh │ ├── setup_nsis.nsi │ ├── setup_nsis_vc08.vcproj │ ├── setup_nsis_vc10.vcxproj │ ├── setup_nsis_vc10.vcxproj.filters │ ├── setup_wix.bat │ ├── setup_wix.wxs │ ├── setup_wix_vc08.vcproj │ ├── setup_wix_vc10.vcxproj │ └── setup_wix_vc10.vcxproj.filters ├── shell/ │ ├── lang_util.cc │ ├── lang_util.hh │ ├── readme.txt │ ├── resource.h │ ├── settings.cc │ ├── settings.hh │ ├── settings_manager.cc │ ├── settings_manager.hh │ ├── shell.cc │ ├── shell.def │ ├── shell.idl │ ├── shell.rc │ ├── shell.rgs │ ├── shell.vcproj.vspscc │ ├── shell_ext.cc │ ├── shell_ext.hh │ ├── shell_ext.rgs │ ├── shell_ps.def │ ├── shell_ps_vc08.vcproj │ ├── shell_ps_vc08.vcproj.vspscc │ ├── shell_vc08.vcproj │ ├── shell_vc10.vcxproj │ ├── shell_vc10.vcxproj.filters │ ├── stdafx.cc │ ├── stdafx.hh │ ├── string_table.cc │ ├── string_table.hh │ └── version.hh ├── tests/ │ ├── codec.hh │ ├── data/ │ │ └── audio/ │ │ ├── audio_test_1-sndfile_ogg-quality_mid.ogg │ │ ├── audio_test_1-sndfile_wma-128.wma │ │ ├── audio_test_1-sndfile_wma-28.wma │ │ ├── audio_test_1-sndfile_wma-64.wma │ │ └── audio_test_1.aif │ ├── tests_vc08.vcproj │ ├── tests_vc10.vcxproj │ └── tests_vc10.vcxproj.filters └── tools/ ├── codectester/ │ ├── codectester.cc │ ├── codectester.hh │ ├── codectester.rc │ ├── codectester_vc08.vcproj │ ├── codectester_vc10.vcxproj │ ├── codectester_vc10.vcxproj.filters │ ├── main_dlg.cc │ ├── main_dlg.hh │ ├── resource.h │ ├── stdafx.cc │ └── stdafx.hh └── translationtool/ ├── lng_analyzer.cc ├── lng_analyzer.hh ├── main_dlg.cc ├── main_dlg.hh ├── resource.h ├── stdafx.cc ├── stdafx.hh ├── translationtool.cc ├── translationtool.hh ├── translationtool.rc ├── translationtool_vc08.vcproj ├── translationtool_vc10.vcxproj └── translationtool_vc10.vcxproj.filters ================================================ FILE CONTENTS ================================================ ================================================ FILE: .gitignore ================================================ /bin/ /dep/cdrtools/ /dep/lame/ /dep/libogg/ /dep/libsndfile/ /dep/libvorbis/ /dep/smoke/ /dist/ /doc/english/infrarecorder.chm /obj/ /output/ /src/_ReSharper.infrarecorder_vc10/* /src/ipch/* /src/shell/dlldata.c /src/shell/shell.hh /src/shell/shell_i.c /src/shell/shell_p.c /src/Win32/ /src/x64/ /src/setup/ir_plugin/Win32/ /src/setup/ir_plugin/x64/ /src/tests/test.cc *.aps *.ncb *.opensdf *.user *.sdf *.suo christian_kindahl.pfx christian_kindahl.psw ================================================ FILE: dep/readme.txt ================================================ Some InfraRecorder components depends on the following 3rd party projects: * cdrtools: http://cdrecord.berlios.de/ * LAME: http://lame.sourceforge.net/ * libogg: http://www.xiph.org/ogg/ * libsndfile: http://www.mega-nerd.com/libsndfile/ * libvorbis: http://www.xiph.org/vorbis/ Since the InfraRecorder solution references the above projects their sources or in some cases binaries must be unpacked to their corresponding subdirectory. ================================================ FILE: doc/english/help_english_vc08.vcproj ================================================ ================================================ FILE: doc/english/help_english_vc10.vcxproj ================================================  Debug Win32 Release Win32 help_english {44E47ABA-9695-4A96-BC52-53585C6AAA3C} help_english MakeFileProj Makefile Makefile <_ProjectFileVersion>10.0.30319.1 $(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ hhc infrarecorder.hhp rem for some reason hhc exits with code 1 even on successful builds. set %ERRORLEVEL%=0 del infrarecorder.chm hhc infrarecorder.hhp rem for some reason hhc exits with code 1 even on successful builds. set %ERRORLEVEL%=0 del infrarecorder.chm help_english.exe WIN32;_DEBUG;$(NMakePreprocessorDefinitions) $(NMakeIncludeSearchPath) $(NMakeForcedIncludes) $(NMakeAssemblySearchPath) $(NMakeForcedUsingAssemblies) $(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ hhc infrarecorder.hhp rem for some reason hhc exits with code 1 even on successful builds. set %ERRORLEVEL%=0 del infrarecorder.chm hhc infrarecorder.hhp rem for some reason hhc exits with code 1 even on successful builds. set %ERRORLEVEL%=0 del infrarecorder.chm help_english.exe WIN32;NDEBUG;$(NMakePreprocessorDefinitions) $(NMakeIncludeSearchPath) $(NMakeForcedIncludes) $(NMakeAssemblySearchPath) $(NMakeForcedUsingAssemblies) $(ExecutablePath) $(ExecutablePath) ================================================ FILE: doc/english/help_english_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav ================================================ FILE: doc/english/how_to_use/burn_image.html ================================================ Burn Image
To burn/record a disc image, you can either use the menu:
Actions Burn Image...
or the toolbar button:

You will be prompted to select the disc image on your hard drive that you want to record.

Options

A detailed description of the available options can be found in this topic.

================================================ FILE: doc/english/how_to_use/burn_options.html ================================================ Burn Options

This topic covers the burn/recording options that appear on various places in InfraRecorder, for example when you want to burn a custom compilation, a disc image, or copy a disc.

Although these options are accessable in many different contexts, as mentioned above, they are always presented in a similar way:

General Settings

On The Fly

When recording on the fly, the file system will be generated while recording, which may increase the risk of write errors. If this option is turned off a temporary disc image will first be created on the hard drive and then recorded to the disc. The preferred setting is usually off; it should generally be enabled only when you are low on disc space.

Verify the Disc After Writing

Enabling this option will cause InfraRecorder to perform a CRC comparison between the files on your hard drive and the files on the newly recorded disc, to make sure that all files have been written to the disc without any problems.

Write Speed

Select the write speed to use when recording the disc. Selecting the Maximum option will automatically select the highest speed that the recorder is capable of.

Write Method

This option selects what method that you want to use when recording the disc. Only the options that your recorder supports will be available in the combo box.

Session-At-Once (SAO) often refered to as Disc-At-Once (DAO) writes all of the data (including lead-in and lead-out) in one pass, not allowing any interruptions in the data stream. Additional session/data cannot be added at a later time. Please note that DVDs must be written using this method.

Track-At-Once (TAO) writes each track independently, which requires link blocks between two tracks. Older recorders often force a two second pause (pregap) between two tracks, whereas newer recorders often can adjust the amount of pregap data (see the option described below).

TAO with zero pregap uses the Track-At-Once method described above and tries to set the pregap data length to zero, minimizing the number of link blocks between the tracks.

Raw writing (raw96r) writes data in raw mode using 2352 byte sectors plus 96 bytes of raw P-W subchannel data, resulting in a sector size of 2448 bytes. This is the preferred raw writing mode, since it gives the best control over the CD writing process.

Raw writing (raw16) writes data in raw mode using 2352 bytes sectors plus 16 bytes of P-Q subchannel data, resulting in a sector size of 2368 bytes. If a recorder does not support the raw96r raw writing mode, this is the preferred raw writing mode. This write method does not support CD-Text.

Raw writing (raw96p) writes data in raw mode using 2352 byte sectors plus 96 bytes of raw P-W subchannel data, resulting in a sector size of 2448 bytes. This is the less preferred raw writing mode, mainly because very few recorders support it and some of these recorders have bugs in the firmware implementation. Don't use this method if your recorder supports the raw96r or raw16 raw writing method.

Important: Please note that raw writing methods requires significantly more CPU-time than the other write methods. If your CPU is too slow you might get problems with buffer underruns.

Other Options

Activating the Simulation option will cause InfraRecorder to perform the selected action but with the recorder's laser turned off. This option is recommended if you are unsure if the operation will succeed or not.

Buffer underrun protection is a feature in most newer recorders which allows the writing process to continue even if a buffer underrun error occurr. This feature often has different names by different vendors, for example: Yamaha Lossless-Link, Sanyo BURN-Proof, Ricoh Just-Link, etc.

The Pad data tracks option will cause each data track to be followed by 15 sectors containing zeros, and audio track data to be padded to be a multiple of 2352 bytes. You might want to enable this option is if your CD-reader has problems reading the last sectors of a track or if you intend to use the disc on a Linux ISO-9660 filesystem with the read ahead bug.

Disabling the Close the disc after writing option will cause the last session (if using SAO mode) or track (if using a TAO mode) not to be closed. This can be useful if you want to record a CD in multiple steps.

Important: Creating a non-closed disc is not the same as creating a multi-session disc.


Advanced Settings

The Allow overburning option allows you to write more than the official size to a medium. Most blank media can hold more space than the official size, as the official size of the lead-out area on a disc is 90 seconds (6750 sectors) and a disc usually works with only 150 sectors of lead-out. All media may be overburned by at least 88 seconds (6600 sectors). Most recorders can do overburning only with the SAO and raw write methods. Some recorders limit overburning and limit a disc to certain size. This problem may be circumvented by writing the CD in raw mode , which gives the recorder no chance to find the medium size before starting the recording process.

When the Swap audio byte order option is enabled, audio data is assumed to be in byte-swapped (little-endian) order. Some types of recorders for example from Yamaha, Sony and the new SCSI-3/MMC recorders require audio data to be presented in little-endian order, while other recorders require audio data to be presented in big-endian (network) byte order normally used by the SCSI protocol. The byte order required by your recorder will automatically be detected. The only time you may want to use this option is if your data stream is in Intel (little-endian) order.

Ignore medium size can be enabled when you want to ignore the known size of the medium. It should be used with extreme care. This option implies overburning.

The Set the SCSI IMMED flag option will, as the name suggest set the IMMED flag for certain SCSI commands. Setting the IMMED flag will request the commands to return immediateley while the operation proceeds in the background, making the bus usable for other devices and avoiding a system freeze. This can be useful on broken systems with ATAPI hard disk and CD/DVD-writer on the same bus or with SCSI systems that don't use disconnect/reconnect. These systems will freeze while blanking or closing a disc, or while the recorder is filling up a session to the minimum amount. Please note that not all recorders support the IMMED flag.

Yamaha Audio Master Q. R. is a feature which is used to create high quality audio discs that have less reading problems in Hi-Fi players. It is implemented as a variant of the SAO write mode so it will only work if you select the Session-At-Once (SAO) write method. This feature does not work with all writing speeds and reduces the amount of data that can be written to a disc, because the pits on the CD will be larger than normal. If this feature is enabled, a 74 minute CD will have the capacity of 63 minutes, and an 80 minute CD will have the capacity reduced to 68 minutes. This feature also works with data discs.

The Forcespeed mode option forces the drive to use the selected write speed no matter of the quality of the medium. Normally modern drives know the highest possible speed for different media and may reduce the speed in order to grant the best write quality. This option should be used with caution, the recorder usually knows better which medium to write at full speed.

The Plextor VariRec write mode allows the user to slightly adjust the power of the laser. If configured properly this may reduce the jitter, resulting in better sound quality and increased playability and compatibility with existing CD-players. VariRec only works when the write speed is set to four.

================================================ FILE: doc/english/how_to_use/configuration.html ================================================ Configuration
To access the InfraRecorder configuration, use the menu:
Options Configuration...

General Settings

The Check if autorun is enabled on each startup option specifies whether you want InfraRecorder to check if autorun enabled on each startup or not. It is recommended that autorun is turned of because leaving autorun enabled causes Windows to poll the CD drive while recording, which might damage your CD.

If you want InfraRecorder to remember the last active folder in the Explorer View you should check the Remember the last active folder option. You can also specify a folder on your own that will be the default every time InfraRecorder starts.

The Temporary folder option lets you specify which folder that should be used when temporarily storing files on your harddrive, for example disc images. If your harddrive/partition (which stores the temporary folder) is almost full it can be a good idea to use a temporary folder on another drive.

Advanced Settings

If you want to enable the log feature of InfraRecorder, enable the Enable program log option. This can be usefull when trying to locate a possible bug/error in InfraRecorder. It's not recommended that you enable log support if you do not intend to log a special event because InfraRecorder requires more memory and CPU-time when the log support is enabled.

The Enable smoke effect option enables or disables the smoke effect displayed during writing processes. The smoke effect requires Windows Vista Aero to be enabled. If Aero is not enabled this option will have no effect.

The FIFO buffer size option lets you specify the size of the RAM buffer that is used in addition to your recorders physical buffer. Icreasing the buffer size may result in a more stable recording process. As a rule of thumb, the FIFO size should be at least equal to the size of the pysical buffer of the CD/DVD-Recorder and no more than half of the physical amount of RAM available in the machine. If you often record discs on-the-fly, this buffer should be large (for example 128 MiB) to prevent buffer underruns.

Language Settings

A list of available languages are displayed in the combo box. To change language, simply select the language you want in the combo box, click the OK-button and restart InfraRecorder. If your language is not available, check the InfraRecorder website to see if a translation in your language exists.

Shell Extension

The shell extension (when enabled) adds additional menu entries to the shell context menu:

It adds the options to record disc images and InfraRecorder projects just by right-clicking on them.

The shell extension can be customized to display the items in a submenu. To display the context menu items in a submenu enable the Display context menu items in a submenu option.

It can also be customized to not display icons on the menu items by disabling the Display menu item icons option.

Register the Shell Extension

The shell extension does not work automatically with disc images and InfraRecorder projects. When enabling the Enalbe InfraRecorder shell extension, InfraRecorder tells Windows Explorer that it offer other applications to use it's extended features.

To make Windows Explorer use the additional features supplied by the InfraRecorder shell extension, the shell extension must be registered with the file types that should be able to use the extra features.

There are a set of predefined file extensions available in the list. To associate the InfraRecorder shell extension with a file type, just check the item in the list view. You can add any additional file types to the list by pressing the Add file extension button:
================================================ FILE: doc/english/how_to_use/copy_audio_disc.html ================================================ Copy Audio Disc
Copying an audio disc requires more steps than copying a data disc. First you must save the audio tracks on your hard drive. To do so, open the tracks dialog by:
Actions Manage Tracks...
The windows should look similar to this screenshot when you have selected your source device and inserted an audio disc:
Now select the tracks you want to save (copy) by clicking and holding the shift or control button. When you have selected the tracks press the save tracks button:

You will now be prompted to select a target directory for the tracks. Please go ahead and select a folder of your choice. When you have selected a folder all the tracks that you have selected will be saved there (unless any major read errors occured).

You next step is to create a new audio project and add the tracks you just saved to it. Please read this topic for more information.

================================================ FILE: doc/english/how_to_use/copy_data_disc.html ================================================ Copy Data Disc

Please note that this page contains information on how to copy a data disc. If you want to copy an audio disc (which is an entirely different process) please see this topic.

When you want to copy a data disc you have two main options which is if you want to copy the disc directly to another drive (for example from a CD-reader to a CD-recorder) or to a disc image on your hard drive.

Copy to a Compact Disc

To copy a disc directly to another drive, use the menu:
Actions Copy Disc to a Compact Disc...
or the toolbar button:

Source

Select the source drive which contains the compact disc that you want to make a copy of.

Target

Select the target drive which contains the empty compact disc that you want to write the copy to. Please note that the target drive can not be the same as the source drive.

On The Fly

Writing on the fly means that the data will be read from the source drive and then directly written to the target (recorder) without any buffering on your hard drive (only a relatively small memory buffer is used). If your source drive would fail to read some sectors on the source disc it might not be able to supply the target (recorder) with data fast enough, resulting in write errors on the target disc. However most new recorder offer some kind of buffer underrun protection technology that should protect the targe disc if this event occurs.

When the On the fly option is disabled a temporary disc image will first be created on your hard drive. The disc image will then be written to the target drive. Using this option requires more free disc space on your hard drive but is recommended in most cases.

Clone Disc

When this option is enabled all sub-channel data and the full TOC on the source disc will also be copied to the target disc. This option must be enabled when copying a mixed-mode disc, otherwise only the data track will be copied. It's recommended that your record the target disc using the raw96r write method. If that method is not supported by your recorder, please try the raw16 write method.

Read Options

The read options are described in this topic.

Other Options

The other options are described in this topic.


Copy to a Disc Image

To copy a disc to a disc image on the hard drive, use the menu:
Actions Copy Disc to a Disc Image...

Source

Select the source drive which contains the compact disc that you want to make a copy of.

Image File

Select the location and name of the disc image. Please note that you will approximateley need the same amount of size avaiable on your hard drive as the compact disc contains.

Read Options

The read options are described in this topic.

================================================ FILE: doc/english/how_to_use/device_configuration.html ================================================ Device Configuration
If you have many any changes in your hardware configuration you probably want to make InfraRecorder aware of the changes. To display the InfraRecorder device configuration, use the menu:
Options Devices...

You will now see a list of devices that have been detected by InfraRecorder. If you want to update the configuration, press the Rescan button. This will cause InfraRecorder to perform a full system scan gather information about all supported devices.

If you want InfraRecorder to silently validate the configuration everytime you start it, enable the Silently validate the configuration at startup option.

================================================ FILE: doc/english/how_to_use/disc_information.html ================================================ Disc Information
To view detailed information about a disc, please use the menu:
Actions Disc Information <select the drive containing the disc that you're interested in>

Field Information

The Disc type field displays what type of disc that is inserted in the drive. For example: CD-R, DVD+R DL.

The Book type field is only valid on DVD discs and displays of what book type the DVD is.

The Region field displays what region encoding the DVD has. The region number can be resolved into the following regions:

  1. United States of America, Canada.
  2. Europe, including France, Greece, Turkey, Egypt, Arabia, Japan and South Africa.
  3. Korea, Thailand, Vietnam, Borneo and Indonesia.
  4. Australia and New Zealand, Mexico, the Caribbean, and South America.
  5. India, Africa, Russia and former USSR countries.
  6. Peoples Republic of China.
  7. Unused.
  8. Airlines and cruise ships.
  9. Expansion (often used as region free).

The Layers field displays the number of layers on the disc.

The Tracks field displays the number of tracks on the disc.

The Sessions field displays the number of sessions on the disc.

The Status field displays information about the disc and session status as well as information on if the disc is erasable or not.

The Used space field displays the amount of used space on the disc.

The Free space field displays the amount of free space on the disc.

================================================ FILE: doc/english/how_to_use/erase_disc.html ================================================ Erase Disc
To erase a rewritable disc, you can either use the menu:
Actions Erase Rewritable Disc...
or the toolbar button:

Recorder

Please select the recorder that you want to use for erasing the disc.

Erase Method

Select one of the four erase methods to use. The Erase the entire disc method will destroy all data on the disc. This operation may take a long time. Using the Minimally erase the disc method will only cause the table of contents (TOC), PMA and pregap to be erased. Basicly the actual data is never erased from the disc (it will not be accessible), the data will instead be overwritten when you write to the disc the next time. This method is very fast can can often be done in about 10 seconds. The Unclose last session method uncloses the last session (on a closed multi-session disc) allowing more sessions to be added to the disc. The last method Erase last session will simply just erase the last session on the disc. This may take long or short time depending on the size of the session.

Other Options

If the table of contents (TOC) for some reason has been damaged on a disc, InfraRecorder will not erase the disc unless the Ignore illegal TOC option is set.

Activating the Simulation option will cause InfraRecorder to perform the selected action but with the recorder's laser turned off. This option is recommended if you are unsure if the operation will succeed or not.

================================================ FILE: doc/english/how_to_use/fixate_disc.html ================================================ Close Disc
A closed disc is a disc that is considered to be finished. Normally a disc is automatically closed after recording data. This tool is useful if data has been written but the disc for some reason hasn't been closed. To close a disc, use the menu:
Actions Close Disc...

Recorder

Please select the recorder that contains the disc that you want to close.

Other Options

Activating the Simulation option will cause InfraRecorder to perform the selected action but with the recorder's laser turned off. This option is recommended if you are unsure if the operation will succeed or not.

================================================ FILE: doc/english/how_to_use/manage_tracks.html ================================================ Manage Tracks
The Manage Tracks tool displays table of contents (TOC) information about a certain disc. It does also offer tools to save and verify selected tracks. To open the track manager, use the menu:
Actions Manage Tracks...

Select the tracks that you want to work with by clicking the mouse while pressing the shift or control key. You can also use the keyboard arrows to navigate and select in the track list.

When you save tracks to your hard drive you will be prompted to select a target directory. The tracks will then automatically be saved and named by their track number and type (Track 1.wav, Track 2.iso). To save the selected tracks to you hard drive, press the save tracks button:
To scan the selected tracks for errors, use the verify tracks button:

Screenshots

The result after verifying a data track:

================================================ FILE: doc/english/how_to_use/read_options.html ================================================ Read Options

This topic covers the read options that appear on various places in InfraRecorder, for example when you want to copy a disc either to a disc image or to another disc.

Altough these options are accessable in many different contexts as mentioned above, they are always presented in a similar way:

Read Settings

Ignore read errors

Enabling this option will cause the high level error checking not to abort when errors are found in the data stream. The drive will also be switched into a mode where it ignores read errors in data sectors that are a result of uncorrectable ECC/EDC errors before reading.

Read all sub-channel data and the full TOC

When this option is enabled the disc will be read with all sub-channel data and a full TOC. The full TOC data will be put into a file with similar name to the specified image name but with the suffix .toc.

Read speed

Select the speed to use when reading the disc. Selecting the Maximum option will automatically select the highest speed that the drive is capable of. Only MMC compliant drives will benefit from this option. The speed of non MMC drives is not changed.

Using a lower speed may increase the readability of a disc.

================================================ FILE: doc/english/how_to_use/working_with_projects/add_boot_image.html ================================================ Add Boot Image

There are several options that you may need to configure when adding a boot image to your project.

Local Path

In this field you should specify the local path of the selected boot image. The path is relative to the root folder of the disc. For example: /boot/ will create a folder called boot in the root that contains the file that you have selected.

Emulation Type

This option lets your specify the type of emulation that should be used on the "El Torino" boot disc. If the emulation type is set to Floppy, the boot image must be exactly the size of a 1200, 1440 or 2880 KiB floppy. If the emulation type is set to Harddisk, the boot image must begin with a master boot record that contains a single partition. Using no emulation will cause the system to load and execute the image without performing any disc emulation.

Advanced Options

The Don't make image bootable option allows you to prevent the disc from beeing marked as bootable. The system will provide an emulated drive for the image, but will boot off a standard boot device.

Enabling the Write boot-info-table to the image option will cause the boot image to be patched at offset 8 with a 54-byte table containing information about the disc layout. If this option is enabled the local boot image that you have specified will be patched, so make sure that you have a backup of this file if it can't be easily regenerated.

The Boot load segment option allows you to specify the load segment address (in hexadecimal) for no-emulation "El Torito" discs.

The Boot load size option allows you to specify the number (in hexadecimal) of virtual (512-byte) sectors to load in no-emulation mode. It's usually recommended to load the entire boot file. Some BIOSes may have problems if this size is not a multiple of 4.

================================================ FILE: doc/english/how_to_use/working_with_projects/getting_started.html ================================================ Getting Started

This topic will help you get started with your first custom CD project. InfraRecorder currently supports three kinds of projects.

Data Disc projects are used for creating discs that contains files and folders (using the ISO9660 filesystem) that can be used on almost any computer. Data discs does not hold as much data per sector as audio discs due to the fact that data discs also stores addition error-check/correction data. As a result of this, data discs can be recorded in higher speed without necessary loose any quality/data. Data discs can be created in multiple steps, allowing data to be added to existing CDs. See this topic for more information on the subject.

Audio Disc projects are used for creating audio discs that will play in any CD-player (and computer). Audio projects should normally be recorded at lower write speeds than data projects because audio discs does not contain any error-checking/correction data.

Mixed-Mode CD projects are used for creating discs that contains one first data track which shares the features of a Data Disc project followed by a number of audio tracks. A Mixed-Mode CD will play in any CD-player, but the first (data) track will sound like noise. The audio tracks will play as normal.

To create a new project, use the menu:
File New Project <select the type of project that you want to create>
To open an existing project, use the menu:
File Open Project...
or the toolbar button:

InfraRecorder projects can be recorded directly to a physical compact disc or to a disc image. A disc image is a file stored on your computer that contains all the file data that you have added to your project (with exception for audio tracks in Mixed-Mode and Audio projects). A disc image can be recorded at a later time. See this topic for more information.

To record your project to a compact disc, you can use the menu:
Actions Burn Compilation to a Compact Disc...
or the toolbar button:

A detailed description of the recording options can be in this topic.

Environment

General

The Explorer View toolbar is used for navigating the explorer view and for adding files that are selected in the explorer list view to your project.
The Disc Layout toolbar is used for project navigation and management.

File Management

The Edit menu is used for project file management:
The options available from the edit menu (above) are also avaiable for faster access by right-clicking in the project view. For example if your right-click on a folder this menu will appear:
If you add more data to your project than what the selected media can contain, the space meter at the bottom of the view will turn red:
The space meter will turn orange if the amount of data added to the project exceeds the offical size of the media but will probably fit on the media if recorded with overburn enabled:

You can change the space meter size to match the actual size of the blank disc that you will record your project on. To do so, right click on the space meter and select the apropriate media size.


File Management

Add Files

There are many different ways to add files to your project. You can use drag and drop from the Explorer View and from Windows Exlporer. You can also navigate the Explore View and select the files you want to include in your project.

When you have selected the files you want, you can use the menu:
Edit Add Selected
or the toolbar button in the Explorer View toolbar:

You can also use the Explorer View to nagivate to a folder and quickly add all files and folder in that folder to your project.

To add all files and folder in the active Explorer View folder, use the menu:
Edit Add All
or the toolbar button in the Explorer View toolbar:

Remove Files

There are several ways of removing files and folders from your project. One way is to press the delete key on your keyboard. You can also use the menu or the toolbar button.

To remove files using the menu, do the following:
Edit Remove
you can also use the toolbar button in the Disc Layout toolbar:

Other Operations

To rename a file or folder, use the menu:
Edit Rename
or the toolbar button in the Disc Layout toolbar:
To add a new empty folder to your project, use the menu:
Edit New Folder
or the toolbar button in the Disc Layout toolbar:
================================================ FILE: doc/english/how_to_use/working_with_projects/multisession_disc.html ================================================ Multi-Session Disc

A multi-session disc is a disc that contains multiple sessions. A multi-session disc can be recorded in multiple steps by recording one session at a time.

Creating New Multi-Session Discs

Creating a new multi-session disc is easy. To create a new multi-session disc, create a new data project:
File New Project Data Disc
Open the project properties:
File Project Properties...
Select the ISO tab and change the Format to:
Mode 2 XA (multisession)

You can now add files and folder to you project as usual. See this topic for more information on how to work with projects.

Continue Multi-Session Discs

To add more data to an existing multi-session disc you must import the existing session data into your project. To do so, use the menu:
Actions Import Session...

A window will popup which allows you to select a device and view how much allocated and free space that is available on the disc. If the OK-button is greyed it means that the disc can not be imported.

When you have selected the device which has the multi-session disc that you want to import inserted. Press the OK-button and the data will be imported into your project. The imported data can not be manipulated or removed from the disc. All imported files and folders are displayed in grey text.

When are done working with the new session and want to add the new data to the disc, either use the menu:
Actions Burn Compilation to a Compact Disc...
or the toolbar button:
================================================ FILE: doc/english/how_to_use/working_with_projects/project_settings.html ================================================ Project Settings
This topic covers the project settings that are accessible from the menu:
File Project Properties...

General Settings

The only general setting that you are able to change is the disc label. The default suggested label is based on the date and time of when the project was created. Please note that the label applies to the same restrictions as general file names in the project (see the ISO Settings section).

ISO Settings

Level

This option sets the ISO conformance level which basicly are different levels of file name restrictions. There are three levels supported in InfraRecorder:

  1. Level 1 uses file names in the 8.3 format (eight characters with a three-character extension), upper case letters, numbers and underscore. The maximum directory depth is eight.
  2. Level 2 allows file names to be up to 31 characters long.
  3. Level 3 allows files to be fragmented (mainly to allow packet writing, or incremental CD recording).
  4. Level 4 does not really exist, but when selected the ISO-9660:1999 (which is ISO-9660 version 2) standard is used. This standard allows file names to be up to 207 characters long and the directory structure may be more than eight levels deep.

Character Set

Defines the character set used in the local file names included in the project. InfraRecorder tries to automatically detect the character set used on your system.

Format

This option specifies the format that should be used when writing your project data to a disc. Mode 1 is normally used when creating regular non multi-session discs while Mode 2 should be used when creating multi-session discs. Mode 1 allows 2048 bytes of data per sector, Mode 2 allows 2336 bytes of data per sector (A CD-ROM sector is 2352 bytes large).

Other Options

The Use Joliet file name extension adds Joliet directory records to the disc in addition to regular ISO9660 file names. The joliet extension is commonly used on Windows systems and allows unicode file names with a maximum length of 64 characters.

If you want to use even longer file names you can enable the Allow more than 64 characters for Joliet names option. This is not fully compatible with the Joliet specification but seems to work. The maximum character length is extended to 103 characters.

The Include UDF support in the generated file system option is self explanatory. UDF support is currently in alpha status, and for this reason it's not possible to generate UDF only filesystems.

The Omit version number from ISO9660 file names option is self explanatory.

Fields

This secion contains options to specify information about the people behind the CD-project. The Publisher, Preparer, System and Volume set fields should be edited directly, the other fields often contains file names due to the limited character length of 36 characters.

Audio Settings

This secion allows you to create CD-Text information. CD-Text is a format supported by some (many?) CD-players that allows track and artist information to be displayed when the CD is playing. These options are available in audio and mixed-mode projects.

Boot Settings

This section is only available on data projects and allows you to specify up to 63 boot images that will be used to create an "El Torito" bootable disc. To add a new boot image to the project, click the Add boot image button:

Boot Catalog

This option specifies the path and filename of the boot catalog to be used when making an "El Torito" bootable disc. The path name should be relative to the root on the disc. The file will be inserted into the output tree and not created in the source filesystem. Please make sure that the specified file name does not conflict with an existing file.

================================================ FILE: doc/english/infra_recorder/acknowledgments.html ================================================ Acknowledgments

InfraRecorder uses icons and derivate work based on the icons in the Tango Icon Project. The derivative work based on the Tango Icons can be separateley downloaded (under the Creative Commons Attribution Share-Alike license) from the official InfraRecorder website.

================================================ FILE: doc/english/infra_recorder/copyright.html ================================================ Copyright

InfraRecorder copyright © 2006-2010 Christian Kindahl.

InfraRecorder works in co-operation with the following software:

================================================ FILE: doc/english/infra_recorder/faq.html ================================================ Frequently Asked Questions

For a more up-to-date list of questions and answers, please visit http://infrarecorder.org.

InfraRecorder does not my disc devices, how do I solve this problem?
This is most likely a permission issue. By default InfraRecorder uses an interface called SPTI to access disc devices. On Windows 2000, XP and 2003 systems administrator permissions are required in order to use SPTI.

If you want to allow limited user accounts to access disc devices using SPTI, please do the following when logged in as an administrator:

  1. Navigate "Start" then "Run" in the Windows start-menu.
  2. Type "secpol.msc" without the quotes and press the OK button.
  3. Navigate "Local Policies" then "Security Options" in the tree.
  4. Change "Devices: Restrict CD-ROM access to locally logged-on user only" item from "Disabled" to "Enabled.".

Please note that some versions of Windows (Windows XP home for example) does not have "secpol.msc". If using such a system please do the following instead (while logged in as an administrator):

  1. Navigate "Start" then "Run" in the Windows start-menu.
  2. Type "regedit" without the quotes and press the OK button.
  3. Navigate "HKEY_LOCAL_MACHINE", "SOFTWARE", "Microsoft", "Windows NT", "CurrentVersion" and finally "Winlogon" in the tree
  4. In the selected path, add a string value named "allocatecdroms" with the value "1" (without the quotes). If the string value already exist with the value "0", simply change it to "1".
================================================ FILE: doc/english/infra_recorder/feature_overview.html ================================================ Feature Overview

This page lists the most essential features of InfraRecorder.

Main Features

Environment

Explorer Integration

Integrates with explorer and adds new shell context menu options.

================================================ FILE: doc/english/infra_recorder/installation.html ================================================ Installation

The InfraRecorder installer supports different options/parameters for unattended installations. The following parameters can be passed to the installer:

/S
Runs the installer (or uninstaller) silently. All options will be default unless overrided by another parameter to the installer.

/LANGUAGE=<language>
Selects the language that InfraRecorder should use. For example: "irsetup.exe /S /LANGUAGE=swedish" will install InfraRecorder silently with the default language set to Swedish.

================================================ FILE: doc/english/infra_recorder/introduction.html ================================================ Introduction

Welcome

Thank you for installing InfraRecorder! InfraRecorder is a free CD burning solution for Microsoft Windows.

Quick Navigation

Feature Overview
License Agreement
System Requirements
Quick Start
Copyright
Acknowledgments
What's New
Installation
================================================ FILE: doc/english/infra_recorder/license_agreement.html ================================================ License Agreement

GNU GENERAL PUBLIC LICENSE

Version 3, 29 June 2007

Copyright © 2007 Free Software Foundation, Inc. <http://fsf.org/>

Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed.

Preamble

The GNU General Public License is a free, copyleft license for software and other kinds of works.

The licenses for most software and other practical works are designed to take away your freedom to share and change the works. By contrast, the GNU General Public License is intended to guarantee your freedom to share and change all versions of a program--to make sure it remains free software for all its users. We, the Free Software Foundation, use the GNU General Public License for most of our software; it applies also to any other work released this way by its authors. You can apply it to your programs, too.

When we speak of free software, we are referring to freedom, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for them if you wish), that you receive source code or can get it if you want it, that you can change the software or use pieces of it in new free programs, and that you know you can do these things.

To protect your rights, we need to prevent others from denying you these rights or asking you to surrender the rights. Therefore, you have certain responsibilities if you distribute copies of the software, or if you modify it: responsibilities to respect the freedom of others.

For example, if you distribute copies of such a program, whether gratis or for a fee, you must pass on to the recipients the same freedoms that you received. You must make sure that they, too, receive or can get the source code. And you must show them these terms so they know their rights.

Developers that use the GNU GPL protect your rights with two steps: (1) assert copyright on the software, and (2) offer you this License giving you legal permission to copy, distribute and/or modify it.

For the developers' and authors' protection, the GPL clearly explains that there is no warranty for this free software. For both users' and authors' sake, the GPL requires that modified versions be marked as changed, so that their problems will not be attributed erroneously to authors of previous versions.

Some devices are designed to deny users access to install or run modified versions of the software inside them, although the manufacturer can do so. This is fundamentally incompatible with the aim of protecting users' freedom to change the software. The systematic pattern of such abuse occurs in the area of products for individuals to use, which is precisely where it is most unacceptable. Therefore, we have designed this version of the GPL to prohibit the practice for those products. If such problems arise substantially in other domains, we stand ready to extend this provision to those domains in future versions of the GPL, as needed to protect the freedom of users.

Finally, every program is threatened constantly by software patents. States should not allow patents to restrict development and use of software on general-purpose computers, but in those that do, we wish to avoid the special danger that patents applied to a free program could make it effectively proprietary. To prevent this, the GPL assures that patents cannot be used to render the program non-free.

The precise terms and conditions for copying, distribution and modification follow.

TERMS AND CONDITIONS

0. Definitions.

“This License” refers to version 3 of the GNU General Public License.

“Copyright” also means copyright-like laws that apply to other kinds of works, such as semiconductor masks.

“The Program” refers to any copyrightable work licensed under this License. Each licensee is addressed as “you”. “Licensees” and “recipients” may be individuals or organizations.

To “modify” a work means to copy from or adapt all or part of the work in a fashion requiring copyright permission, other than the making of an exact copy. The resulting work is called a “modified version” of the earlier work or a work “based on” the earlier work.

A “covered work” means either the unmodified Program or a work based on the Program.

To “propagate” a work means to do anything with it that, without permission, would make you directly or secondarily liable for infringement under applicable copyright law, except executing it on a computer or modifying a private copy. Propagation includes copying, distribution (with or without modification), making available to the public, and in some countries other activities as well.

To “convey” a work means any kind of propagation that enables other parties to make or receive copies. Mere interaction with a user through a computer network, with no transfer of a copy, is not conveying.

An interactive user interface displays “Appropriate Legal Notices” to the extent that it includes a convenient and prominently visible feature that (1) displays an appropriate copyright notice, and (2) tells the user that there is no warranty for the work (except to the extent that warranties are provided), that licensees may convey the work under this License, and how to view a copy of this License. If the interface presents a list of user commands or options, such as a menu, a prominent item in the list meets this criterion.

1. Source Code.

The “source code” for a work means the preferred form of the work for making modifications to it. “Object code” means any non-source form of a work.

A “Standard Interface” means an interface that either is an official standard defined by a recognized standards body, or, in the case of interfaces specified for a particular programming language, one that is widely used among developers working in that language.

The “System Libraries” of an executable work include anything, other than the work as a whole, that (a) is included in the normal form of packaging a Major Component, but which is not part of that Major Component, and (b) serves only to enable use of the work with that Major Component, or to implement a Standard Interface for which an implementation is available to the public in source code form. A “Major Component”, in this context, means a major essential component (kernel, window system, and so on) of the specific operating system (if any) on which the executable work runs, or a compiler used to produce the work, or an object code interpreter used to run it.

The “Corresponding Source” for a work in object code form means all the source code needed to generate, install, and (for an executable work) run the object code and to modify the work, including scripts to control those activities. However, it does not include the work's System Libraries, or general-purpose tools or generally available free programs which are used unmodified in performing those activities but which are not part of the work. For example, Corresponding Source includes interface definition files associated with source files for the work, and the source code for shared libraries and dynamically linked subprograms that the work is specifically designed to require, such as by intimate data communication or control flow between those subprograms and other parts of the work.

The Corresponding Source need not include anything that users can regenerate automatically from other parts of the Corresponding Source.

The Corresponding Source for a work in source code form is that same work.

2. Basic Permissions.

All rights granted under this License are granted for the term of copyright on the Program, and are irrevocable provided the stated conditions are met. This License explicitly affirms your unlimited permission to run the unmodified Program. The output from running a covered work is covered by this License only if the output, given its content, constitutes a covered work. This License acknowledges your rights of fair use or other equivalent, as provided by copyright law.

You may make, run and propagate covered works that you do not convey, without conditions so long as your license otherwise remains in force. You may convey covered works to others for the sole purpose of having them make modifications exclusively for you, or provide you with facilities for running those works, provided that you comply with the terms of this License in conveying all material for which you do not control copyright. Those thus making or running the covered works for you must do so exclusively on your behalf, under your direction and control, on terms that prohibit them from making any copies of your copyrighted material outside their relationship with you.

Conveying under any other circumstances is permitted solely under the conditions stated below. Sublicensing is not allowed; section 10 makes it unnecessary.

3. Protecting Users' Legal Rights From Anti-Circumvention Law.

No covered work shall be deemed part of an effective technological measure under any applicable law fulfilling obligations under article 11 of the WIPO copyright treaty adopted on 20 December 1996, or similar laws prohibiting or restricting circumvention of such measures.

When you convey a covered work, you waive any legal power to forbid circumvention of technological measures to the extent such circumvention is effected by exercising rights under this License with respect to the covered work, and you disclaim any intention to limit operation or modification of the work as a means of enforcing, against the work's users, your or third parties' legal rights to forbid circumvention of technological measures.

4. Conveying Verbatim Copies.

You may convey verbatim copies of the Program's source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice; keep intact all notices stating that this License and any non-permissive terms added in accord with section 7 apply to the code; keep intact all notices of the absence of any warranty; and give all recipients a copy of this License along with the Program.

You may charge any price or no price for each copy that you convey, and you may offer support or warranty protection for a fee.

5. Conveying Modified Source Versions.

You may convey a work based on the Program, or the modifications to produce it from the Program, in the form of source code under the terms of section 4, provided that you also meet all of these conditions:

A compilation of a covered work with other separate and independent works, which are not by their nature extensions of the covered work, and which are not combined with it such as to form a larger program, in or on a volume of a storage or distribution medium, is called an “aggregate” if the compilation and its resulting copyright are not used to limit the access or legal rights of the compilation's users beyond what the individual works permit. Inclusion of a covered work in an aggregate does not cause this License to apply to the other parts of the aggregate.

6. Conveying Non-Source Forms.

You may convey a covered work in object code form under the terms of sections 4 and 5, provided that you also convey the machine-readable Corresponding Source under the terms of this License, in one of these ways:

A separable portion of the object code, whose source code is excluded from the Corresponding Source as a System Library, need not be included in conveying the object code work.

A “User Product” is either (1) a “consumer product”, which means any tangible personal property which is normally used for personal, family, or household purposes, or (2) anything designed or sold for incorporation into a dwelling. In determining whether a product is a consumer product, doubtful cases shall be resolved in favor of coverage. For a particular product received by a particular user, “normally used” refers to a typical or common use of that class of product, regardless of the status of the particular user or of the way in which the particular user actually uses, or expects or is expected to use, the product. A product is a consumer product regardless of whether the product has substantial commercial, industrial or non-consumer uses, unless such uses represent the only significant mode of use of the product.

“Installation Information” for a User Product means any methods, procedures, authorization keys, or other information required to install and execute modified versions of a covered work in that User Product from a modified version of its Corresponding Source. The information must suffice to ensure that the continued functioning of the modified object code is in no case prevented or interfered with solely because modification has been made.

If you convey an object code work under this section in, or with, or specifically for use in, a User Product, and the conveying occurs as part of a transaction in which the right of possession and use of the User Product is transferred to the recipient in perpetuity or for a fixed term (regardless of how the transaction is characterized), the Corresponding Source conveyed under this section must be accompanied by the Installation Information. But this requirement does not apply if neither you nor any third party retains the ability to install modified object code on the User Product (for example, the work has been installed in ROM).

The requirement to provide Installation Information does not include a requirement to continue to provide support service, warranty, or updates for a work that has been modified or installed by the recipient, or for the User Product in which it has been modified or installed. Access to a network may be denied when the modification itself materially and adversely affects the operation of the network or violates the rules and protocols for communication across the network.

Corresponding Source conveyed, and Installation Information provided, in accord with this section must be in a format that is publicly documented (and with an implementation available to the public in source code form), and must require no special password or key for unpacking, reading or copying.

7. Additional Terms.

“Additional permissions” are terms that supplement the terms of this License by making exceptions from one or more of its conditions. Additional permissions that are applicable to the entire Program shall be treated as though they were included in this License, to the extent that they are valid under applicable law. If additional permissions apply only to part of the Program, that part may be used separately under those permissions, but the entire Program remains governed by this License without regard to the additional permissions.

When you convey a copy of a covered work, you may at your option remove any additional permissions from that copy, or from any part of it. (Additional permissions may be written to require their own removal in certain cases when you modify the work.) You may place additional permissions on material, added by you to a covered work, for which you have or can give appropriate copyright permission.

Notwithstanding any other provision of this License, for material you add to a covered work, you may (if authorized by the copyright holders of that material) supplement the terms of this License with terms:

All other non-permissive additional terms are considered “further restrictions” within the meaning of section 10. If the Program as you received it, or any part of it, contains a notice stating that it is governed by this License along with a term that is a further restriction, you may remove that term. If a license document contains a further restriction but permits relicensing or conveying under this License, you may add to a covered work material governed by the terms of that license document, provided that the further restriction does not survive such relicensing or conveying.

If you add terms to a covered work in accord with this section, you must place, in the relevant source files, a statement of the additional terms that apply to those files, or a notice indicating where to find the applicable terms.

Additional terms, permissive or non-permissive, may be stated in the form of a separately written license, or stated as exceptions; the above requirements apply either way.

8. Termination.

You may not propagate or modify a covered work except as expressly provided under this License. Any attempt otherwise to propagate or modify it is void, and will automatically terminate your rights under this License (including any patent licenses granted under the third paragraph of section 11).

However, if you cease all violation of this License, then your license from a particular copyright holder is reinstated (a) provisionally, unless and until the copyright holder explicitly and finally terminates your license, and (b) permanently, if the copyright holder fails to notify you of the violation by some reasonable means prior to 60 days after the cessation.

Moreover, your license from a particular copyright holder is reinstated permanently if the copyright holder notifies you of the violation by some reasonable means, this is the first time you have received notice of violation of this License (for any work) from that copyright holder, and you cure the violation prior to 30 days after your receipt of the notice.

Termination of your rights under this section does not terminate the licenses of parties who have received copies or rights from you under this License. If your rights have been terminated and not permanently reinstated, you do not qualify to receive new licenses for the same material under section 10.

9. Acceptance Not Required for Having Copies.

You are not required to accept this License in order to receive or run a copy of the Program. Ancillary propagation of a covered work occurring solely as a consequence of using peer-to-peer transmission to receive a copy likewise does not require acceptance. However, nothing other than this License grants you permission to propagate or modify any covered work. These actions infringe copyright if you do not accept this License. Therefore, by modifying or propagating a covered work, you indicate your acceptance of this License to do so.

10. Automatic Licensing of Downstream Recipients.

Each time you convey a covered work, the recipient automatically receives a license from the original licensors, to run, modify and propagate that work, subject to this License. You are not responsible for enforcing compliance by third parties with this License.

An “entity transaction” is a transaction transferring control of an organization, or substantially all assets of one, or subdividing an organization, or merging organizations. If propagation of a covered work results from an entity transaction, each party to that transaction who receives a copy of the work also receives whatever licenses to the work the party's predecessor in interest had or could give under the previous paragraph, plus a right to possession of the Corresponding Source of the work from the predecessor in interest, if the predecessor has it or can get it with reasonable efforts.

You may not impose any further restrictions on the exercise of the rights granted or affirmed under this License. For example, you may not impose a license fee, royalty, or other charge for exercise of rights granted under this License, and you may not initiate litigation (including a cross-claim or counterclaim in a lawsuit) alleging that any patent claim is infringed by making, using, selling, offering for sale, or importing the Program or any portion of it.

11. Patents.

A “contributor” is a copyright holder who authorizes use under this License of the Program or a work on which the Program is based. The work thus licensed is called the contributor's “contributor version”.

A contributor's “essential patent claims” are all patent claims owned or controlled by the contributor, whether already acquired or hereafter acquired, that would be infringed by some manner, permitted by this License, of making, using, or selling its contributor version, but do not include claims that would be infringed only as a consequence of further modification of the contributor version. For purposes of this definition, “control” includes the right to grant patent sublicenses in a manner consistent with the requirements of this License.

Each contributor grants you a non-exclusive, worldwide, royalty-free patent license under the contributor's essential patent claims, to make, use, sell, offer for sale, import and otherwise run, modify and propagate the contents of its contributor version.

In the following three paragraphs, a “patent license” is any express agreement or commitment, however denominated, not to enforce a patent (such as an express permission to practice a patent or covenant not to sue for patent infringement). To “grant” such a patent license to a party means to make such an agreement or commitment not to enforce a patent against the party.

If you convey a covered work, knowingly relying on a patent license, and the Corresponding Source of the work is not available for anyone to copy, free of charge and under the terms of this License, through a publicly available network server or other readily accessible means, then you must either (1) cause the Corresponding Source to be so available, or (2) arrange to deprive yourself of the benefit of the patent license for this particular work, or (3) arrange, in a manner consistent with the requirements of this License, to extend the patent license to downstream recipients. “Knowingly relying” means you have actual knowledge that, but for the patent license, your conveying the covered work in a country, or your recipient's use of the covered work in a country, would infringe one or more identifiable patents in that country that you have reason to believe are valid.

If, pursuant to or in connection with a single transaction or arrangement, you convey, or propagate by procuring conveyance of, a covered work, and grant a patent license to some of the parties receiving the covered work authorizing them to use, propagate, modify or convey a specific copy of the covered work, then the patent license you grant is automatically extended to all recipients of the covered work and works based on it.

A patent license is “discriminatory” if it does not include within the scope of its coverage, prohibits the exercise of, or is conditioned on the non-exercise of one or more of the rights that are specifically granted under this License. You may not convey a covered work if you are a party to an arrangement with a third party that is in the business of distributing software, under which you make payment to the third party based on the extent of your activity of conveying the work, and under which the third party grants, to any of the parties who would receive the covered work from you, a discriminatory patent license (a) in connection with copies of the covered work conveyed by you (or copies made from those copies), or (b) primarily for and in connection with specific products or compilations that contain the covered work, unless you entered into that arrangement, or that patent license was granted, prior to 28 March 2007.

Nothing in this License shall be construed as excluding or limiting any implied license or other defenses to infringement that may otherwise be available to you under applicable patent law.

12. No Surrender of Others' Freedom.

If conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot convey a covered work so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not convey it at all. For example, if you agree to terms that obligate you to collect a royalty for further conveying from those to whom you convey the Program, the only way you could satisfy both those terms and this License would be to refrain entirely from conveying the Program.

13. Use with the GNU Affero General Public License.

Notwithstanding any other provision of this License, you have permission to link or combine any covered work with a work licensed under version 3 of the GNU Affero General Public License into a single combined work, and to convey the resulting work. The terms of this License will continue to apply to the part which is the covered work, but the special requirements of the GNU Affero General Public License, section 13, concerning interaction through a network will apply to the combination as such.

14. Revised Versions of this License.

The Free Software Foundation may publish revised and/or new versions of the GNU General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns.

Each version is given a distinguishing version number. If the Program specifies that a certain numbered version of the GNU General Public License “or any later version” applies to it, you have the option of following the terms and conditions either of that numbered version or of any later version published by the Free Software Foundation. If the Program does not specify a version number of the GNU General Public License, you may choose any version ever published by the Free Software Foundation.

If the Program specifies that a proxy can decide which future versions of the GNU General Public License can be used, that proxy's public statement of acceptance of a version permanently authorizes you to choose that version for the Program.

Later license versions may give you additional or different permissions. However, no additional obligations are imposed on any author or copyright holder as a result of your choosing to follow a later version.

15. Disclaimer of Warranty.

THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM “AS IS” WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.

16. Limitation of Liability.

IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.

17. Interpretation of Sections 15 and 16.

If the disclaimer of warranty and limitation of liability provided above cannot be given local legal effect according to their terms, reviewing courts shall apply local law that most closely approximates an absolute waiver of all civil liability in connection with the Program, unless a warranty or assumption of liability accompanies a copy of the Program in return for a fee.

END OF TERMS AND CONDITIONS

How to Apply These Terms to Your New Programs

If you develop a new program, and you want it to be of the greatest possible use to the public, the best way to achieve this is to make it free software which everyone can redistribute and change under these terms.

To do so, attach the following notices to the program. It is safest to attach them to the start of each source file to most effectively state the exclusion of warranty; and each file should have at least the “copyright” line and a pointer to where the full notice is found.

    <one line to give the program's name and a brief idea of what it does.>
    Copyright (C) <year>  <name of author>

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.

Also add information on how to contact you by electronic and paper mail.

If the program does terminal interaction, make it output a short notice like this when it starts in an interactive mode:

    <program>  Copyright (C) <year>  <name of author>

    This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
    This is free software, and you are welcome to redistribute it
    under certain conditions; type `show c' for details.

The hypothetical commands `show w' and `show c' should show the appropriate parts of the General Public License. Of course, your program's commands might be different; for a GUI interface, you would use an “about box”.

You should also get your employer (if you work as a programmer) or school, if any, to sign a “copyright disclaimer” for the program, if necessary. For more information on this, and how to apply and follow the GNU GPL, see <http://www.gnu.org/licenses/>.

The GNU General Public License does not permit incorporating your program into proprietary programs. If your program is a subroutine library, you may consider it more useful to permit linking proprietary applications with the library. If this is what you want to do, use the GNU Lesser General Public License instead of this License. But first, please read <http://www.gnu.org/philosophy/why-not-lgpl.html>.

================================================ FILE: doc/english/infra_recorder/quick_start.html ================================================ Quick Start

How to Use?

Getting Started
Multi-Session Discs
Copy Data Discs
Copy Audio Discs
Erase Rewritable Discs
View Disc Information
Configure Devices
================================================ FILE: doc/english/infra_recorder/system_requirements.html ================================================ System Requirements

InfraRecorder has the following system requirements:

================================================ FILE: doc/english/infra_recorder/whats_new.html ================================================ What's New

Version 0.53.0.0

Version 0.52.0.0

Version 0.51.0.0

Version 0.50.0.0

Version 0.46.2.0

Version 0.46.1.0

Version 0.46.0.0

Version 0.45.0.0

Version 0.44.1.0

Version 0.44.0.0

Version 0.43.1.0

Version 0.43.0.0

Version 0.42.1.0

Version 0.42.0.0

Version 0.41.0.0

Version 0.40.0.0

Version 0.31.0.0

Version 0.30.0.83

Version 0.30.0.82 (Beta 2)

================================================ FILE: doc/english/infrarecorder.hhc ================================================ ================================================ FILE: doc/english/infrarecorder.hhk ================================================ ================================================ FILE: doc/english/infrarecorder.hhp ================================================ [OPTIONS] Compatibility=1.1 or later Compiled file=infrarecorder.chm Contents file=infrarecorder.hhc Default topic=infra_recorder\introduction.html Display compile progress=No Full-text search=Yes Index file=infrarecorder.hhk Language=0x409 English (United States) Title=InfraRecorder Help [INFOTYPES] ================================================ FILE: doc/english/style.css ================================================ body { font-weight: normal; font-size: 11px; margin: 0px; color: #000000; font-family: Verdana, Arial, Helvetica, sans-serif; height: 100%; background-color: #ffffff; text-align: left } h1 { font-size: 115%; margin-top: 1em; margin-bottom: .6em; } h2 { font-size: 100%; margin-top: 1em; margin-bottom: .6em; } ul { list-style-type: disc; margin-left: 1.9em; margin-top: .6em; margin-bottom: 0em; } ol { margin-left: 2.9em; margin-top: .6em; margin-bottom: 0em; font-weight: bold; } ol span { font-weight: normal; } li { margin-bottom: .3em; } p,dl { margin-top: .6em; margin-bottom: .6em; } hr { margin-top: .6em; } dd { padding-top: .2em; margin-bottom: .6em; margin-left: 0.8em; } #header { background: #ccccff; border-bottom: 1px solid #9999ff; padding-top: 5px; padding-left: 10px; padding-bottom: 5px; } #location { font-style: italic; } #topic { font-weight: bold; } #content { padding: 10px; padding-left: 10px; overflow: auto; height: 100%; } ================================================ FILE: doc/english/stylescript.js ================================================ window.onload = OnSize; window.onresize = OnSize; function OnSize() { var vHeader = document.all.item("header"); var vContent = document.all.item("content"); if (vContent ==null) return; if (vHeader != null) { document.all.content.style.overflow = "auto"; document.all.header.style.width = document.body.offsetWidth; document.all.content.style.width = document.body.offsetWidth - 4; document.all.content.style.top = document.all.header.offsetHeight; if (document.body.offsetHeight > document.all.header.offsetHeight) { document.all.content.style.height = document.body.offsetHeight - document.all.header.offsetHeight - 3; } else { document.all.content.style.height = 0; } } } ================================================ FILE: doc/french/Gpl-3.0-FR.txt ================================================ LICENCE PUBLIQUE GNRALE GNU Version 3, du 29 juin 2007. Copyright (C) 2007 Free Software Foundation, Inc. Chacun est autoris copier et distribuer des copies conformes de ce document de licence, mais toute modification en est proscrite. Traduction franaise par Philippe Verdy , le 30 juin 2007. _______________________________________________________________________ Avertissement important au sujet de cette traduction franaise. _______________________________________________________________________ Ceci est une traduction en franais de la licence GNU General Public License (GPL). Cette traduction est fournie ici dans lespoir quelle facilitera sa comprhension, mais elle ne constitue pas une traduction officielle ou approuve dun point de vue juridique. La Free Software Foundation (FSF) ne publie pas cette traduction et ne la pas approuve en tant que substitut valide au plan lgal pour la licence authentique GNU General Public Licence. Cette traduction na pas encore t passe en revue attentivement par un juriste et donc le traducteur ne peut garantir avec certitude quelle reprsente avec exactitude la signification lgale des termes de la licence authentique GNU General Public License publie en anglais. Cette traduction ntablit donc lgalement aucun des termes et conditions dutilisation dun logiciel sous licence GNU GPL seul le texte original en anglais le fait. Si vous souhaitez tre sr que les activits que vous projetez seront autorises par la GNU General Public License, veuillez vous rfrer sa seule version anglaise authentique. La FSF vous recommande fermement de ne pas utiliser cette traduction en tant que termes officiels pour vos propres programmes ; veuillez plutt utiliser la version anglaise authentique telle que publie par la FSF. Si vous choisissez dacheminer cette traduction en mme temps quun Programme sous licence GNU GPL, cela ne vous dispense pas de lobligation dacheminer en mme temps une copie de la licence authentique en anglais, et de conserver dans la traduction cet avertissement important en franais et son quivalent en anglais ci-dessous. _______________________________________________________________________ Important Warning About This French Translation. _______________________________________________________________________ This is a translation of the GNU General Public License (GPL) into French. This translation is distributed in the hope that it will facilitate understanding, but it is not an official or legally approved translation. The Free Software Foundation (FSF) is not the publisher of this translation and has not approved it as a legal substitute for the authentic GNU General Public License. The translation has not been reviewed carefully by lawyers, and therefore the translator cannot be sure that it exactly represents the legal meaning of the authentic GNU General Public License published in English. This translation does not legally state the terms and conditions of use of any Program licenced under GNU GPL only the original English text of the GNU LGPL does that. If you wish to be sure whether your planned activities are permitted by the GNU General Public License, please refer to its sole authentic English version. The FSF strongly urges you not to use this translation as the official distribution terms for your programs; instead, please use the authentic English version published by the FSF. If you choose to convey this translation along with a Program covered by the GPL Licence, this does not remove your obligation to convey at the same time a copy of the authentic GNU GPL License in English, and you must keep in this translation this important warning in English and its equivalent in French above. _______________________________________________________________________ Prambule La Licence Publique Gnrale GNU (GNU General Public License) est une licence libre, en copyleft, destine aux uvres logicielles et dautres types de travaux. Les licences de la plupart des uvres logicielles et autres travaux de pratique sont conues pour ter votre libert de partager et modifier ces travaux. En contraste, la Licence Publique Gnrale GNU a pour but de garantir votre libert de partager et changer toutes les versions dun programme afin dassurer quil restera libre pour tous les utilisateurs. Nous, la Free Software Foundation, utilisons la Licence Publique Gnrale GNU pour la plupart de nos logiciels ; cela sapplique aussi tout autre travail dit de cette faon par ses auteurs. Vous pouvez, vous aussi, lappliquer vos propres programmes. Quand nous parlons de logiciel libre (free), nous nous rfrons la libert (freedom), pas au prix. Nos Licences Publiques Gnrales sont conues pour assurer que vous ayez la libert de distribuer des copies de logiciel libre (et le facturer si vous le souhaitez), que vous receviez le code source ou pouviez lobtenir si vous le voulez, que vous pouviez modifier le logiciel ou en utiliser toute partie dans de nouveaux logiciels libres, et que vous sachiez que vous avez le droit de faire tout ceci. Pour protger vos droits, nous avons besoin dempcher que dautres vous restreignent ces droits ou vous demande de leur abandonner ces droits. En consquence, vous avez certaines responsabilits si vous distribuez des copies dun tel programme ou si vous le modifiez : les responsabilits de respecter la libert des autres. Par exemple, si vous distribuez des copies dun tel programme, que ce soit gratuit ou contre un paiement, vous devez accorder aux Destinataires les mmes liberts que vous avez reues. Vous devez aussi vous assurer queux aussi reoivent ou peuvent recevoir son code source. Et vous devez leur montrer les termes de cette licence afin quils connaissent leurs droits. Les dveloppeurs qui utilisent la GPL GNU protgent vos droits en deux tapes : (1) ils affirment leur droits dauteur (copyright) sur le logiciel, et (2) vous accordent cette Licence qui vous donne la permission lgale de le copier, le distribuer et/ou le modifier. Pour la protection des dveloppeurs et auteurs, la GPL stipule clairement quil ny a pas de garantie pour ce logiciel libre. Aux fins la fois des utilisateurs et auteurs, la GPL require que les versions modifies soient marques comme changes, afin que leurs problmes ne soient pas attribus de faon errone aux auteurs des versions prcdentes. Certains dispositifs sont conus pour empcher laccs des utilisateurs linstallation ou lexcution de versions modifies du logiciel lintrieur de ces dispositifs, alors que les fabricants le peuvent. Ceci est fondamentalement incompatible avec le but de protger la libert des utilisateurs de modifier le logiciel. Laspect systmatique de tels abus se produit dans le secteur des produits destins aux utilisateurs individuels, ce qui est prcidment ce qui est le plus inacceptable. Aussi, nous avons conu cette version de la GPL pour prohiber cette pratique pour ces produits. Si de tels problmes surviennent dans dautres domaines, nous nous tenons prt tendre cette restriction ces domaines dans de futures versions de la GPL, autant quil sera ncessaire pour protger la libert des utilisateurs. Finalement, chaque programme est constamment menac par les brevets logiciels. Les tats ne devraient pas autoriser de tels brevets restreindre le dveloppement et lutilisation de logiciels libres sur des ordinateurs dusage gnral ; mais dans ceux qui le font, nous voulons spcialement viter le danger que les brevets appliqus un programme libre puisse le rendre effectivement propritaire. Pour empcher ceci, la GPL assure que les brevets ne peuvent tre utiliss pour rendre le programme non-libre. Les termes prcis et conditions concernant la copie, la distribution et la modification suivent. TERMES ET CONDITIONS Article 0. Dfinitions. Cette Licence se rfre la version 3 de la GNU General Public License (le texte original en anglais). Droit dAuteur signifie aussi les droits du copyright ou voisins qui sappliquent dautres types de travaux, tels que ceux sur les masques de semi-conducteurs. Le Programme se rfre tout travail qui peut tre sujet au Droit dAuteur (copyright) et dont les droits dutilisation sont concds en vertu de cette Licence. Chacun des Licencis, qui cette Licence est concde, est dsign par vous. Les Licencis et les Destinataires peuvent tre des personnes physiques ou morales (individus ou organisations). Modifier un travail signifie en obtenir une copie et adapter tout ou partie du travail dune faon ncessitant une autorisation dun titulaire de Droit dAuteur, autre que celle permettant den produire une copie conforme. Le travail rsultant est appel une version modifie du prcdent travail, ou un travail bas sur le prcdent travail. Un Travail Couvert signifie soit le Programme non modifi soit un travail bas sur le Programme. Propager un travail signifie faire quoi que ce soit avec lui qui, sans permission, vous rendrait directement ou indirectement responsable dun dlit de contrefaon suivant les lois relatives au Droit dAuteur, lexception de son excution sur un ordinateur ou de la modification dune copie prive. La propagation inclue la copie, la distribution (avec ou sans modification), la mise disposition envers le public, et aussi d'autres activits dans certains pays. Acheminer un travail signifie tout moyen de propagation de celui-ci qui permet dautres parties de raliser ou recevoir des copies. La simple interaction dun utilisateur travers un rseau informatique, sans transfert effectif dune copie, ne constitue pas un acheminement. Une interface utilisateur interactive affiche des Notices Lgales Appropries quand elle comprend un dispositif convenable, bien visible et vident qui (1) affiche une notice approprie sur les droits dauteur et (2) informe lutilisateur quil ny a pas de garantie pour le travail (sauf si des garanties ont t fournies hors du cadre de cette Licence), que les licencis peuvent acheminer le travail sous cette Licence, et comment voir une copie de cette Licence. Si linterface prsente une liste de commandes utilisateur ou doptions, tel quun menu, un lment vident dans la liste prsente remplit ce critre. Article 1. Code source. Le code source dun travail signifie la forme prfre du travail permettant ou facilitant les modifications de celui-ci. Le code objet dun travail signifie toute forme du travail qui nen est pas le code source. Une Interface Standard signifie une interface qui est soit celle dune norme officielle dfinie par un organisme de normalisation reconnu ou, dans le cas des interfaces spcifies pour un langage de programmation particulier, une interface largement utilise parmi les dveloppeurs travaillant dans ce langage. Les Bibliothques Systme dun travail excutable incluent tout ce qui, en dehors du travail dans son ensemble, (a) est inclus dans la forme usuelle de paquetage dun Composant Majeur mais ne fait pas partie de ce Composant Majeur et (b) sert seulement permettre lutilisation du travail avec ce Composant Majeur ou implmenter une Interface Standard pour laquelle une implmentation est disponible au public sous forme de code source ; un Composant Majeur signifie, dans ce contexte, un composant majeur essentiel (noyau, systme de fentrage, etc.) du systme dexploitation (le cas chant) dun systme sur lequel le travail excutable fonctionne, ou bien un compilateur utilis pour produire le code objet du travail, ou un interprte de code objet utilis pour excuter celui-ci. Le Source Correspondant dun travail sous forme de code objet signifie lensemble des codes sources ncessaires pour gnrer, installer et (dans le cas dun travail excutable) excuter le code objet et modifier le travail, y compris les scripts pour contrler ces activits. Cependant, cela ninclue pas les Bibliothques Systme du travail, ni les outils dusage gnral ou les programmes libres gnralement disponibles qui peuvent tre utiliss sans modification pour achever ces activits mais ne sont pas partie de ce travail. Par exemple le Source Correspondant inclut les fichiers de dfinition dinterfaces associs aux fichiers sources du travail, et le code source des bibliothques partages et des sous-routines lies dynamiquement, pour lesquelles le travail est spcifiquement conu pour les requrir via, par exemple, des communications de donnes ou contrles de flux internes entre ces sous-programmes et dautres parties du travail. Le Source Correspondant na pas besoin dinclure tout ce que les utilisateurs peuvent regnrer automatiquement partir dautres parties du Source Correspondant. Le Source Correspondant pour un travail sous forme de code source est ce mme travail. Article 2. Permissions de base. Tous les droits accords suivant cette Licence le sont jusquau terme des Droits dAuteur (copyright) sur le Programme, et sont irrvocables pourvu que les conditions tablies soient remplies. Cette Licence affirme explicitement votre permission illimite dexcuter le Programme non modifi. La sortie produite par lexcution dun Travail Couvert nest couverte par cette Licence que si cette sortie, tant donn leur contenu, constitue un Travail Couvert. Cette Licence reconnait vos propres droits dusage raisonnable (fair use en lgislation des tats-Unis dAmrique) ou autres quivalents, tels quils sont pourvus par la loi applicable sur le Droit dAuteur (copyright). Vous pouvez crer, excuter et propager sans condition des Travaux Couverts que vous nacheminez pas, aussi longtemps que votre licence demeure en vigueur. Vous pouvez acheminer des Travaux Couverts dautres personnes dans le seul but de leur faire raliser des modifications votre usage exclusif, ou pour quils vous fournissent des facilits vous permettant dexcuter ces travaux, pourvu que vous vous conformiez aux termes de cette Licence lors de lacheminement de tout matriel dont vous ne contrlez pas le Droit dAuteur (copyright). Ceux qui, ds lors, ralisent ou excutent pour vous les Travaux Couverts ne doivent alors le faire quexclusivement pour votre propre compte, sous votre direction et votre contrle, suivant des termes qui leur interdisent de raliser, en dehors de leurs relations avec vous, toute copie de votre matriel soumis au Droit dAuteur. Lacheminement dans toutes les autres circonstances nest permis que selon les conditions tablies ci-dessous. La concession de sous-licences nest pas autoris ; larticle 10 rend cet usage non ncessaire. Article 3. Protection des droits lgaux des utilisateurs envers les lois anti-contournement. Aucun Travail Couvert ne doit tre vu comme faisant partie dune mesure technologique effective selon toute loi applicable remplissant les obligations prvues larticle 11 du trait international sur le droit dauteur adopt lOMPI le 20 dcembre 1996, ou toutes lois similaires qui prohibent ou restreignent le contournement de telles mesures. Si vous acheminez un Travail Couvert, vous renoncez tout pouvoir lgal dinterdire le contournement des mesures technologiques dans tous les cas o un tel contournement serait effectu en exerant les droits prvus dans cette Licence pour ce Travail Couvert, et vous dclarez rejeter toute intention de limiter lopration ou la modification du Travail, en tant que moyens de renforcer, lencontre des utilisateurs de ce Travail, vos droits lgaux ou ceux de tierces parties dinterdire le contournement des mesures technologiques. Article 4. Acheminement des copies conformes. Vous pouvez acheminer des copies conformes du code source du Programme tel que vous lavez reu, sur nimporte quel support, pourvu que vous publiiez scrupuleusement et de faon approprie sur chaque copie une notice de Droit dAuteur approprie ; gardez intactes toutes les notices tablissant que cette Licence et tous les termes additionnels non permissifs ajouts en accord avec larticle 7 sappliquent ce code ; et donnez chacun des Destinataires une copie de cette Licence en mme temps que le Programme. Vous pouvez facturer un prix quelconque, y compris gratuit, chacune des copies que vous acheminez, et vous pouvez offrir une protection additionnelle de support ou de garantie en change dun paiement. Article 5. Acheminement des versions sources modifies. Vous pouvez acheminer un travail bas sur le Programme, ou bien les modifications pour le produire partir du Programme, sous la forme de code source suivant les termes de larticle 4, pourvu que vous satisfassiez aussi chacune des conditions requises suivantes : a) Le travail doit comporter des notices videntes tablissant que vous lavez modifi et donnant la date correspondante. b) Le travail doit comporter des notices videntes tablissant quil est dit selon cette Licence et les conditions ajoutes daprs larticle 7. Cette obligation vient modifier lobligation de larticle 4 de garder intactes toutes les notices. c) Vous devez licencier le travail entier, comme un tout, suivant cette Licence quiconque entre en possession dune copie. Cette Licence sappliquera en consquence, avec les termes additionnels applicables prvus par larticle 7, la totalit du travail et chacune de ses parties, indpendamment de la faon dont ils sont empaquets. Cette licence ne donne aucune permission de licencier le travail dune autre faon, mais elle ninvalide pas une telle permission si vous lavez reue sparment. d) Si le travail a des interfaces utilisateurs interactives, chacune doit afficher les Notices Lgales Appropries ; cependant si le Programme a des interfaces qui naffichent pas les Notices Lgales Appropries, votre travail na pas les modifier pour quelles les affichent. Une compilation dun Travail Couvert avec dautres travaux spars et indpendants, qui ne sont pas par leur nature des extensions du Travail Couvert, et qui ne sont pas combins avec lui de faon former un programme plus large, dans ou sur un volume de stockage ou un support de distribution, est appel un aggrgat si la compilation et son Droit dAuteur rsultant ne sont pas utiliss pour limiter laccs ou les droits lgaux des utilisateurs de la compilation en dea de ce que permettent les travaux individuels. Linclusion dun Travail Couvert dans un aggrgat ne cause pas lapplication de cette Licence aux autres parties de laggrgat. Article 6. Acheminement des formes non sources. Vous pouvez acheminer sous forme de code objet un Travail Couvert suivant les termes des articles 4 et 5, pourvu que vous acheminiez galement suivant les termes de cette Licence le Source Correspondant lisible par une machine, dune des faons suivantes : a) Acheminer le code objet sur, ou inclus dans, un produit physique (y compris un support de distribution physique), accompagn par le Source Correspondant fix sur un support physique durable habituellement utilis pour les changes de logiciels. b) Acheminer le code objet sur, ou inclus dans, un produit physique (y compris un support de distribution physique), accompagn dune offre crite, valide pour au moins trois annes et valide pour aussi longtemps que vous fournissez des pices de rechange ou un support client pour ce modle de produit, afin de donner quiconque possde le code objet soit (1) une copie du Source Correspondant tout logiciel dans ce produit qui est couvert par cette Licence, sur un support physique durable habituellement utilis pour les changes de logiciels, pour un prix non suprieur au cot raisonnable de la ralisation physique de lacheminement de la source, ou soit (2) un accs permettant de copier le Source Correspondant depuis un serveur rseau sans frais. c) Acheminer des copies individuelles du code objet avec une copie de loffre crite de fournir le Source Correspondant. Cette alternative est permise seulement occasionellement et non commercialement, et seulement si vous avez reu le code objet avec une telle offre, en accord avec larticle 6 alina b. d) Acheminer le code objet en offrant un accs depuis un emplacement dsign (gratuit ou contre facturation) et offrir un accs quivalent au Source Correspondant de la mme faon via le mme emplacement et sans facturation supplmentaire. Vous navez pas besoin dobliger les Destinataires copier le Source Correspondant en mme temps que le code objet. Si lemplacement pour copier le code objet est un serveur rseau, le Source Correspondant peut tre sur un serveur diffrent (opr par vous ou par un tiers) qui supporte des facilits quivalentes de copie, pourvu que vous mainteniez des directions claires proximit du code objet indiquant o trouver le Source Correspondant. Indpendamment de quel serveur hberge le Source Correspondant, vous restez oblig de vous assurer quil reste disponible aussi longtemps que ncessaire pour satisfaire ces obligations. e) Acheminer le code objet en utilisant une transmission dgal--gal, pourvu que vous informiez les autres participants sur o le code objet et le Source Correspondant du travail sont offerts sans frais au public gnral suivant larticle 6 alina d. Une portion sparable du code objet, dont le code source est exclu du Source Correspondant en tant que Bibliothque Systme, na pas besoin dtre inclu dans lacheminement du travail sous forme de code objet. Un Produit Utilisateur est soit (1) un Produit de Consommation, ce qui signifie toute proprit personnelle tangible normalement utilise des fins personnelles, familiales ou relatives au foyer, soit (2) toute chose conue ou vendue pour lincorporation dans un lieu dhabitation. Pour dterminer si un produit constitue un Produit de Consommation, les cas ambigus sont rsolus en fonction de la couverture. Pour un produit particulier reu par un utilisateur particulier, lexpression normalement utilise ci-avant se rfre une utilisation typique ou lusage commun de produits de mme catgorie, indpendamment du statut de cet utilisateur particulier ou de la faon spcifique dont cet utilisateur particulier utilise effectivement ou sattend lui-mme ou est attendu utiliser ce produit. Un produit est un Produit de Consommation indpendamment du fait que ce produit a ou na pas dutilisations substantielles commerciales, industrielles ou hors Consommation, moins que de telles utilisations reprsentent le seul mode significatif dutilisation du produit. Les Informations dInstallation dun Produit Utilisateur signifient toutes les mthodes, procdures, cls dautorisation ou autres informations requises pour installer et excuter des versions modifies dun Travail Couvert dans ce Produit Utilisateur partir dune version modifie de son Source Correspondant. Les informations qui suffisent assurer la continuit de fonctionnement du code objet modifi ne doivent en aucun cas tre empches ou interfres du seul fait quune modification a t effectue. Si vous acheminez le code objet dun Travail Couvert dans, ou avec, ou spcifiquement pour lutilisation dans, un Produit Utilisateur et lacheminement se produit en tant qulment dune transaction dans laquelle le droit de possession et dutilisation du Produit Utilisateur est transfr au Destinataire dfinitivement ou pour un terme fix (indpendamment de la faon dont la transaction est caractrise), le Source Correspondant achemin selon cet article-ci doit tre accompagn des Informations dInstallation. Mais cette obligation ne sapplique pas si ni vous ni aucune tierce partie ne dtient la possibilit dintaller un code objet modifi sur le Produit Utilisateur (par exemple, le travail a t install en mmoire morte). Lobligation de fournir les Informations dInstallation ninclue pas celle de continuer fournir un service de support, une garantie ou des mises jour pour un travail qui a t modifi ou install par le Destinataire, ou pour le Produit Utilisateur dans lequel il a t modifi ou install. Laccs un rseau peut tre rejet quand la modification elle-mme affecte matriellement et dfavorablement les oprations du rseau ou viole les rgles et protocoles de communication au travers du rseau. Le Source Correspondant achemin et les Informations dInstallation fournies, en accord avec cet article, doivent tre dans un format publiquement document (et dont une implmentation est disponible auprs du public sous forme de code source) et ne doit ncessiter aucune cl ou mot de passe spcial pour le dpaquetage, la lecture ou la copie. Article 7. Termes additionnels. Les permissions additionelles dsignent les termes qui supplmentent ceux de cette Licence en mettant des exceptions lune ou plusieurs de ses conditions. Les permissions additionnelles qui sont applicables au Programme entier doivent tre traites comme si elles taient incluent dans cette Licence, dans les limites de leur validit suivant la loi applicable. Si des permissions additionnelles sappliquent seulement une partie du Programme, cette partie peut tre utilise sparment suivant ces permissions, mais le Programme tout entier reste gouvern par cette Licence sans regard aux permissions additionelles. Quand vous acheminez une copie dun Travail Couvert, vous pouvez votre convenance ter toute permission additionelle de cette copie, ou de nimporte quelle partie de celui-ci. (Des permissions additionnelles peuvent tre rdiges de faon requrir leur propre suppression dans certains cas o vous modifiez le travail.) Vous pouvez placer les permissions additionnelles sur le matriel achemin, ajoutes par vous un Travail Couvert pour lequel vous avez ou pouvez donner les permissions de Droit dAuteur (copyright) appropries. Nonobstant toute autre clause de cette Licence, pour tout constituant que vous ajoutez un Travail Couvert, vous pouvez (si autoris par les titulaires de Droit dAuteur pour ce constituant) supplmenter les termes de cette Licence avec des termes : a) qui rejettent la garantie ou limitent la responsabilit de faon diffrente des termes des articles 15 et 16 de cette Licence ; ou b) qui requirent la prservation de notices lgales raisonnables spcifies ou les attributions dauteur dans ce constituant ou dans les Notices Lgales Appropries affiches par les travaux qui le contiennent ; ou c) qui prohibent la reprsentation incorrecte de lorigine de ce constituant, ou qui requirent que les versions modifies dun tel constituant soit marques par des moyens raisonnables comme diffrentes de la version originale ; ou d) qui limitent lusage but publicitaire des noms des concdants de licence et des auteurs du constituant ; ou e) qui refusent accorder des droits selon la lgislation relative aux marques commerciales, pour lutilisation dans des noms commerciaux, marques commerciales ou marques de services ; ou f) qui requirent lindemnisation des concdants de licences et auteurs du constituant par quiconque achemine ce constituant (ou des versions modifies de celui-ci) en assumant contractuellement la responsabilit envers le Destinataire, pour toute responsabilit que ces engagements contractuels imposent directement ces octroyants de licences et auteurs. Tous les autres termes additionnels non permissifs sont considrs comme des restrictions avances dans le sens de larticle 10. Si le Programme tel que vous lavez reu, ou toute partie de celui-ci, contient une notice tablissant quil est gouvern par cette Licence en mme temps quun terme qui est une restriction avance, vous pouvez ter ce terme. Si un document de licence contient une restriction avance mais permet la reconcession de licence ou lacheminement suivant cette Licence, vous pouvez ajouter un Travail Couvert constituant gouvern par les termes de ce document de licence, pourvu que la restriction avance ne survit pas un telle cession de licence ou acheminement. Si vous ajoutez des termes un Travail Couvert en accord avec cet article, vous devez placer, dans les fichiers sources appropris, une dclaration des termes additionnels qui sappliquent ces fichiers, ou une notice indiquant o trouver les termes applicables. Les termes additionnels, quils soient permissifs ou non permissifs, peuvent tre tablis sous la forme dune licence crite sparment, ou tablis comme des exceptions ; les obligations ci-dessus sappliquent dans chacun de ces cas. Article 8. Terminaison. Vous ne pouvez ni propager ni modifier un Travail Couvert autrement que suivant les termes de cette Licence. Toute autre tentative de le propager ou le modifier est nulle et terminera automatiquement vos droits selon cette Licence (y compris toute licence de brevet accorde selon le troisime paragraphe de larticle 11). Cependant, si vous cessez toute violation de cette Licence, alors votre licence depuis un titulaire de Droit dAuteur (copyright) est rinstaure (a) titre provisoire moins que et jusqu ce que le titulaire de Droit dAuteur termine finalement et explicitement votre licence, et (b) de faon permanente si le titulaire de Droit dAuteur ne parvient pas vous notifier de la violation par quelque moyen raisonnable dans les soixante (60) jours aprs la cessation. De plus, votre licence depuis un titulaire particulier de Droit dAuteur est rinstaure de faon permanente si ce titulaire vous notifie de la violation par quelque moyen raisonnable, cest la premire fois que vous avez reu une notification deviolation de cette Licence (pour un travail quelconque) depuis ce titulaire de Droit dAuteur, et vous rsolvez la violation dans les trente (30) jours qui suivent votre rception de la notification. La terminaison de vos droits suivant cette section ne terminera pas les licences des parties qui ont reu des copies ou droits de votre part suivant cette Licence. Si vos droits ont t termins et non rinstaurs de faon permanente, vous ntes plus qualifi recevoir de nouvelles licences pour les mmes constituants selon larticle 10. Article 9. Acceptation non requise pour obtenir des copies. Vous ntes pas oblig daccepter cette licence afin de recevoir ou excuter une copie du Programme. La propagation asservie dun Travail Couvert qui se produit simplement en consquence dune transmission dgal--gal pour recevoir une copie ne ncessite pas lacceptation. Cependant, rien dautre que cette Licence ne vous accorde la permission de propager ou modifier un quelconque Travail Couvert. Ces actions enfreignent le Droit dAuteur si vous nacceptez pas cette Licence. Par consquent, en modifiant ou propageant un Travail Couvert, vous indiquez votre acceptation de cette Licence pour agir ainsi. Article 10. Cession automatique de Licence aux Destinataires et intermdiaires. Chaque fois que vous acheminez un Travail Couvert, le Destinataire reoit automatiquement une licence depuis les concdants originaux, pour excuter, modifier et propager ce travail, suivant les termes de cette Licence. Vous ntes pas responsable du renforcement de la conformation des tierces parties avec cette Licence. Une transaction dentit dsigne une transaction qui transfre le contrle dune organisation, ou de substantiellement tous ses actifs, ou la subdivision dune organisation, ou la fusion de plusieurs organisations. Si la propagation dun Travail Couvert rsulte dune transaction dentit, chaque partie cette transaction qui reoit une copie du travail reoit aussi les licences pour le travail que le prdcesseur intress cette partie avait ou pourrait donner selon le paragraphe prcdent, plus un droit de possession du Source Correspondant de ce travail depuis le prdcesseur intress si ce prdcesseur en dispose ou peut lobtenir par des efforts raisonnables. Vous ne pouvez imposer aucune restriction avance dans lexercice des droits accords ou affirms selon cette Licence. Par exemple, vous ne pouvez imposer aucun paiement pour la licence, aucune royaltie, ni aucune autre charge pour lexercice des droits accords selon cette Licence ; et vous ne pouvez amorcer aucun litige judiciaire (y compris une rclamation croise ou contre-rclamation dans un procs) sur lallgation quune revendication de brevet est enfreinte par la ralisation, lutilisation, la vente, loffre de vente, ou limportation du Programme ou dune quelconque portion de celui-ci. Article 11. Brevets. Un contributeur est un titulaire de Droit dAuteur (copyright) qui autorise lutilisation selon cette Licence du Programme ou du travail sur lequel le Programme est bas. Le travail ainsi soumis licence est appel la version contributive de ce contributeur. Les revendications de brevet essentielles sont toutes les revendications de brevets dtenues ou contrles par le contributeur, quelles soient dj acquises par lui ou acquises subsquemment, qui pourraient tre enfreintes de quelque manire, permises par cette Licence, sur la ralisation, lutilisation ou la vente de la version contributive de celui-ci. Aux fins de cette dfinition, le contrle inclue le droit de concder des sous-licences de brevets dune manire consistante, ncessaire et suffisante, avec les obligations de cette Licence. Chaque contributeur vous accorde une licence de brevet non exclusive, mondiale et libre de toute royaltie, selon les revendications de brevet essentielles, pour raliser, utiliser, vendre, offrir la vente, importer et autrement excuter, modifier et propager les contenus de sa version contributive. Dans les trois paragraphes suivants, une licence de brevet dsigne tous les accords ou engagements exprims, quel que soit le nom que vous lui donnez, de ne pas mettre en vigueur un brevet (telle quune permission explicite pour mettre en pratique un brevet, ou un accord pour ne pas poursuivre un Destinataire pour cause de violation de brevet). Accorder une telle licence de brevet une partie signifie conclure un tel accord ou engagement ne pas faire appliquer le brevet cette partie. Si vous acheminez un Travail Couvert, dpendant en connaissance dune licence de brevet, et si le Source Correspondant du travail nest pas disponible quiconque copie, sans frais et suivant les termes de cette Licence, travers un serveur rseau publiquement acessible ou tout autre moyen immdiatement accessible, alors vous devez soit (1) rendre la Source Correspondante ainsi disponible, soit (2) vous engager vous priver pour vous-mme du bnfice de la licence de brevet pour ce travail particulier, soit (3) vous engager, dune faon consistante avec les obligations de cette Licence, tendre la licence de brevet aux Destinataires de ce travail. Dpendant en connaissance signifie que vous avez effectivement connaissance que, selon la licence de brevet, votre acheminement du Travail Couvert dans un pays, ou lutilisation du Travail Couvert par votre Destinataire dans un pays, infreindrait un ou plusieurs brevets identifiables dans ce pays o vous avez des raisons de penser quils sont valides. Si, conformment ou en liaison avec une mme transaction ou un mme arrangement, vous acheminez, ou propagez en procurant un acheminement de, un Travail Couvert et accordez une licence de brevet lune des parties recevant le Travail Couvert pour lui permettre dutiliser, propager, modifier ou acheminer une copie spcifique du Travail Couvert, alors votre accord est automatiquement tendu tous les Destinataires du Travail Couvert et des travaux bass sur celui-ci. Une licence de brevet est discriminatoire si, dans le champ de sa couverture, elle ninclut pas un ou plusieurs des droits qui sont spcifiquement accords selon cette Licence, ou en prohibe lexercice, ou est conditionne par le non-exercice dun ou plusieurs de ces droits. Vous ne pouvez pas acheminer un Travail Couvert si vous tes partie un arrangement selon lequel une partie tierce exerant son activit dans la distribution de logiciels et laquelle vous effectuez un paiement fond sur ltendue de votre activit dacheminement du travail, et selon lequel la partie tierce accorde, une quelconque partie qui recevrait depuis vous le Travail Couvert, une licence de brevet discriminatoire (a) en relation avec les copies du Travail Couvert achemines par vous (ou les copies ralises partir de ces copies), ou (b) avant tout destine et en relation avec des produits spcifiques ou compilations contenant le Travail Couvert, moins que vous ayez conclu cet arrangement ou que la licence de brevet ait t accorde avant le 28 mars 2007. Rien dans cette Licence ne devrait tre interprt comme devant exclure ou limiter toute licence implicite ou dautres moyens de dfense une infraction qui vous seraient autrement disponible selon la loi applicable relative aux brevets. Article 12. Non abandon de la libert des autres. Si des conditions vous sont imposes (que ce soit par dcision judiciaire, par un accord ou autrement) qui contredisent les conditions de cette Licence, elles ne vous excusent pas des conditions de cette Licence. Si vous ne pouvez pas acheminer un Travail Couvert de faon satisfaire simultnment vos obligations suivant cette Licence et toutes autres obligations pertinentes, alors en consquence vous ne pouvez pas du tout lacheminer. Par exemple, si vous avez un accord sur des termes qui vous obligent collecter pour le racheminement des royalties depuis ceux qui vous acheminez le Programme, la seule faon qui puisse vous permettre de satisfaire la fois ces termes et ceux de cette Licence sera de vous abstenir entirement dacheminer le Programme. Article 13. Utilisation avec la Licence Gnrale Publique Affero GNU. Nonobstant toute autre clause de cette Licence, vous avez la permission de lier ou combiner tout Travail Couvert avec un travail plac sous la version 3 de la Licence Gnrale Publique GNU Affero (GNU Affero General Public License) en un seul travail combin, et dacheminer le travail rsultant. Les termes de cette Licence continueront sappliquer la partie formant un Travail Couvert, mais les obligations spciales de la Licence Gnrale Publique GNU Affero, article 13, concernant linteraction travers un rseau sappliqueront la combinaison en tant que telle. Article 14. Versions rvises de cette License. La Free Software Foundation peut publier des versions rvises et/ou nouvelles de la Licence Publique Gnrale GNU (GNU General Public License) de temps en temps. De telles version nouvelles resteront similaires dans lesprit avec la prsente version, mais peuvent diffrer dans le dtail afin de traiter de nouveaux problmes ou proccupations. Chaque version reoit un numro de version distinctif. Si le Programme indique quune version spcifique de la Licence Publique Gnrale GNU ou toute version ultrieure (or any later version) sapplique celui-ci, vous avez le choix de suivre soit les termes et conditions de cette version numrote, soit ceux de nimporte quelle version publie ultrieurement par la Free Software Foundation. Si le Programme nindique pas une version spcifique de la Licence Publique Gnrale GNU, vous pouvez choisir lune quelconque des versions qui ont t publies par la Free Software Foundation. Si le Programme spcifie quun intermdiaire peut dcider quelles versions futures de la Licence Gnrale Publique GNU peut tre utilise, la dclaration publique dacceptation dune version par cet intermdiaire vous autorise choisir cette version pour le Programme. Des versions ultrieures de la licence peuvent vous donner des permissions additionelles ou diffrentes. Cependant aucune obligation additionelle nest impose lun des auteurs ou titulaires de Droit dAuteur du fait de votre choix de suivre une version ultrieure. Article 15. Dclaration dabsence de garantie. IL NY A AUCUNE GARANTIE POUR LE PROGRAMME, DANS LES LIMITES PERMISES PAR LA LOI APPLICABLE. MOINS QUE CELA NE SOIT TABLI DIFFREMMENT PAR CRIT, LES PROPRITAIRES DE DROITS ET/OU LES AUTRES PARTIES FOURNISSENT LE PROGRAMME EN LTAT SANS GARANTIE DAUCUNE SORTE, QUELLE SOIT EXPRIME OU IMPLICITE, CECI COMPRENANT, SANS SE LIMITER CELLES-CI, LES GARANTIES IMPLICITES DE COMMERCIALISABILIT ET DADQUATION UN OBJECTIF PARTICULIER. VOUS ASSUMEZ LE RISQUE ENTIER CONCERNANT LA QUALIT ET LES PERFORMANCES DU PROGRAMME. DANS LVENTUALIT O LE PROGRAMME SAVRERAIT DFECTUEUX, VOUS ASSUMEZ LES COTS DE TOUS LES SERVICES, RPARATIONS OU CORRECTIONS NCESSAIRES. Article 16. Limitation de responsabilit. EN AUCUNE AUTRE CIRCONSTANCE QUE CELLES REQUISES PAR LA LOI APPLICABLE OU ACCORDES PAR CRIT, UN TITULAIRE DE DROITS SUR LE PROGRAMME, OU TOUT AUTRE PARTIE QUI MODIFIE OU ACHEMINE LE PROGRAMME COMME PERMIS CI-DESSUS, NE PEUT TRE TENU POUR RESPONSABLE ENVERS VOUS POUR LES DOMMAGES, INCLUANT TOUT DOMMAGE GNRAL, SPCIAL, ACCIDENTEL OU INDUIT SURVENANT PAR SUITE DE LUTILISATION OU DE LINCAPACIT DUTILISER LE PROGRAMME (Y COMPRIS, SANS SE LIMITER CELLES-CI, LA PERTE DE DONNES OU LINEXACTITUDE DES DONNES RETOURNES OU LES PERTES SUBIES PAR VOUS OU DES PARTIES TIERCES OU LINCAPACIT DU PROGRAMME FONCTIONNER AVEC TOUT AUTRE PROGRAMME), MME SI UN TEL TITULAIRE OU TOUTE AUTRE PARTIE A T AVIS DE LA POSSIBILIT DE TELS DOMMAGES. Article 17. Interprtation des sections 15 et 16. Si la dclaration dabsence de garantie et la limitation de responsabilit fournies ci-dessus ne peuvent prendre effet localement selon leurs termes, les cours de justice qui les examinent doivent appliquer la lgislation locale qui approche au plus prs possible une leve absolue de toute responsabilit civile lie au Programme, moins quune garantie ou assumation de responsabilit accompagne une copie du Programme en change dun paiement. FIN DES TERMES ET CONDITIONS. _______________________________________________________________________ Comment appliquer ces termes vos nouveaux programmes Si vous dveloppez un nouveau programme et voulez quil soit le plus possible utilisable par le public, la meilleure faon dy parvenir et den faire un logiciel libre que chacun peut redistribuer et changer suivant ces termes-ci. Pour appliquer ces termes, attachez les notices suivantes au programme. Il est plus sr de les attacher au dbut de chacun des fichiers sources afin de transporter de faon la plus effective possible lexclusion de garantie ; et chaque fichier devrait comporter au moins la ligne de rservation de droit (copyright) et une indication permettant de savoir o la notice complte peut tre trouve : Copyright (C) Tous droits rservs. Ce programme est un logiciel libre ; vous pouvez le redistribuer ou le modifier suivant les termes de la GNU General Public License telle que publie par la Free Software Foundation : soit la version 3 de cette licence, soit ( votre gr) toute version ultrieure. Ce programme est distribu dans lespoir quil vous sera utile, mais SANS AUCUNE GARANTIE : sans mme la garantie implicite de COMMERCIALISABILIT ni dADQUATION UN OBJECTIF PARTICULIER. Consultez la Licence Gnrale Publique GNU pour plus de dtails. Vous devriez avoir reu une copie de la Licence Gnrale Publique GNU avec ce programme ; si ce nest pas le cas, consultez : . Ajoutez galement les informations permettant de vous contacter par courrier lectronique ou postal. Si le programme produit une interaction sur un terminal, faites lui afficher une courte notice comme celle-ci lors de son dmarrage en mode interactif : Copyright (C) Ce programme vient SANS ABSOLUMENT AUCUNE GARANTIE ; taper affiche g pour les dtails. Ceci est un logiciel libre et vous tes invit le redistribuer suivant certaines conditions ; taper affiche c pour les dtails. Les commandes hypothtiques affiche g and affiche c devrait afficher les parties appropries de la Licence Gnrale Publique. Bien sr, les commandes de votre programme peuvent tre diffrentes ; pour une interface graphique, vous pourriez utiliser une bote propos. Vous devriez galement obtenir de votre employeur (si vous travaillez en tant que programmeur) ou de votre cole un renoncement aux droits de proprit pour ce programme, si ncessaire. Pour plus dinformations ce sujet, et comment appliquer la GPL GNU, consultez . La Licence Gnrale Publique GNU ne permet pas dincorporer votre programme dans des programmes propritaires. Si votre programme est une bibliothque de sous-routines, vous pourriez considrer quil serait plus utile de permettre de lier des applications propritaires avec la bibliothque. Si cest ce que vous voulez faire, utilisez la Licence Gnrale Publique Limite GNU au lieu de cette Licence ; mais dabord, veuillez lire . _______________________________________________________________________ ================================================ FILE: doc/french/InfraRecorder.hhp ================================================ [OPTIONS] Compatibility=1.1 or later Compiled file=French.chm Contents file=InfraRecorderFR.hhc Default topic=infra_recorder\introduction.html Display compile progress=No Full text search stop list file=fr.stp Full-text search=Yes Index file=InfraRecorderFR.hhk Language=0x809 English (United Kingdom) Title=Aide InfraRecorder [INFOTYPES] ================================================ FILE: doc/french/InfraRecorderFR.hhc ================================================
================================================ FILE: doc/french/InfraRecorderFR.hhk ================================================
================================================ FILE: doc/french/fr.stp ================================================ alors au aucuns aussi autre avant avec avoir bon car ce cela ces ceux chaque ci comme comment dans des du dedans dehors depuis deux devrait doit donc dos droite dbut elle elles en encore essai est et eu fait faites fois font force haut hors ici il ils je juste la le les leur l ma maintenant mais mes mine moins mon mot mme ni nomms notre nous nouveaux ou o par parce parole pas personnes peut peu pice plupart pour pourquoi quand que quel quelle quelles quels qui sa sans ses seulement si sien son sont sous soyez sujet sur ta tandis tellement tels tes ton tous tout trop trs tu valeur voie voient vont votre vous vu a taient tat tions t tre ================================================ FILE: doc/french/how_to_use/burn_image.html ================================================ Graver une image disque
Pour graver ou enregistrer une image disque, vous pouvez soit passer par le menu:
Actions Graver l'image...
ou par le bouton de la barre d'outils:

Il vous sera demand de slectionner l'image disque, sur votre disque dur, que vous souhaitez gravez.

Options

Une description dtaille des options disponible apparat dans cette section.

================================================ FILE: doc/french/how_to_use/burn_options.html ================================================ Options de gravure

Cette section concerne les options de gravure qui peuvent tre appeles de plusieurs endroit dans InfraRecorder. Par exemple, lorsque vous souhaitez votre propre compilation, une image disque ou faire une copie d'un disque.

Bien que ces options soient accessibles dans diffrents contextes, l'interface se prsente toujours de la mme manire :

Paramtres gnraux

A la vole

Lorsqu'on grave la vole, tout le systme de fichiers sera gnr au moment de la gravure, ce qui peut augmenter le risque d'erreur d'criture. Si cette option est invalide, une image temporaire du disque sera gnre sur le disque dur, puis enregistre sur le disque graver. Par dfaut, cette option est invalide. Elle ne devrait tre valid que si vous manquez d'espace sur votre disque dur.

Vrifier le disque aprs criture

En validant cette option, InfraRecorder effectuera une comparaison CRC entre les fichiers sources sur votre disque dur, et les fichiers cibles qui se trouvent sur le disque qui vient d'tre grav afin de s'assurer qu'aucune erreur d'criture ne s'est produite sur le disque.

Vitesse d'criture

Slectionne la vitesse de gravure sur le disque. En slectionnant l'option Maximum, la vitesse la plus haute supporte par le disque ou la graveur sera utilise.

Mthode d'criture

Cette option slectionne la mthode d'criture utilise lors de la gravure du disque. Seules les mthodes supportes par votre graveur seront listes.

Session-At-Once (SAO) appel aussi Disc-At-Once (DAO) , cette mthode crit toutes les donnes (lead-in et lead-out inclus) en une seule passe. Sans autoriser aucune interruption dans le flux de donnes. Aucune session ou donnes ne peuvent tre ajoutes ultrieurement sur le disque. Notez que les DVD doivent obligatoirement tre gravs suivant cette mthode.

Track-At-Once (TAO) crit chaque piste indpendemment ce qui requiert des blocs de lien entre deux pistes. Les anciens graveurs crent souvent une pause de deux secondes entre les piste (appel pregap) alors que les graveurs les plus rcents autorisent un ajustement de la dure du pregap (voir l'option dcrite plus bas).

TAO pregap zro utilise la mthode Track-At-Once dcrite plus haut en essayant de dfinir une dure de pregap zro en rduisant au maximum le nombre de blocs de lien entre  deux pistes.

Ecriture directe (raw96r) crit les donnes brutes en utilisant des secteurs de 2352 octets plus 96 octets du sous canal P-W crant ainsi des secteur de 2448 octets. Il s'agit de la mthode la plus courante d'criture en direct car le contrle de l'criture sur le CD est bien plus fiable.

Ecriture directe (raw16) crit les donnes brutes en utilisant des secteurs de 2352 octets plus 16 octets du sous canal P-Q crant ainsi des secteur de 2368 octets. Cette mthode sera utilis si un graveur ne supporte pas l'criture directe (raw96r). Cette mthode d'criture ne prendra pas en charge les CD-Text.

Ecriture directe (raw96p) crit les donnes brutes en utilisant des secteurs de 2352 octets plus 96 octets du sous canal P-W crant ainsi des secteur de 2448 octets. Cette mthode est viter dans la mesure o peu de graveurs la supportent, et beaucoup de ces graveurs ont des bogues dans leur firmware. N'utilisez pas cette mthode sir votre graveur supporte l'criture directe raw96r ou raw16.

Important: Notez que l'criture directe a un besoin de puissance processeur bien plus important que pour les autres mthodes. Si votre processeur est trs lent, vous pouvez rencontrer des problmes perte de mmoire tampon lors de la gravure.

Autres options

La validation de l'option Simulation va faire en sorte que Infrarecorder va effectuer les oprations demands mais avec le laser du graveur teint. Cette option est recommend si vous souhaitez vous assurer que la gravure du projet se droulera correctement ou pas.

Protection "Buffer underrun" est une focntionnalit prsente sur les graveurs les plus rcents qui autorise la poursuite de la gravure mme si la mmoire tampon du graveur se vide compltement. Cette fonctionnalit peut avoir des noms diffrents suivant les marques d'quipement avec par exemple: Yamaha Lossless-Link, Sanyo BURN-Proof, Ricoh Just-Link, etc. Le nom le plus communment rencontr pour cette fonctionnalit est  BURN-Proof.

Si l'option Complte les donnes des pistes (Pad data tracks) est valid, 15 secteurs nulls seront crit aprs chaque piste de donnes ou audio. Cette option sera utilis dans le cas ou votre lecteur as des difficults lire les derniers secteurs d'une piste. Cette option est aussi utile dans le cas ou vous souhaitez utiliser le disque avec un systme de fichier Linux ISO-9660 contenant un bogue dit "read ahead".

Si vous invalidez l'option Finaliser le disque aprs criture, la dernire session (si vous utilisez le mode SAO) ou la dernire piste (dans le cas d'un mode TAO) ne sera pas ferme. Ceci peut s'avrer utile si vous souhaitez graver un CD en plusieurs tapes.

Important: La cration d'un disque non finalis ne correspond pas la cration d'un disque multi-session.


Paramtres avancs

L'option Autoriser l'overburning permet de graver au dela de la taille officielle du mdia. Le fait est que la plupart des mdias vierges peuvent supporter plus que leur taille officielle, car la zone alloue au "lead-out" est de 90 secondes (soit 6750 secteurs), et qu'un disque fonctionne avec seulement 150 secteurs affects au "lead-out". Les mdias peuvent ainsi tre surchargs d'au moins 88 secondes (6600 secteurs). Le majorit des graveur ne supporte l'overburning qu'en mode d'criture SAO ou raw. Certains graveur ne vous autorisent pas non plus de surcharger le disque comme vous le souhaiteriez, et peuvent limiter la taille du disque. Ce problme peut cependant tre contourn en gravant en mode raw, car dans ce cas, le graveur n'a aucune chance de connatre la taille du disque avant le lancement de la gravure.

Lorsque l'option Echanger l'ordre des octets audio est valide, cela suppose que l'ordre des octets est invers (little endian). Certains modle de graveurs de Yamaha ou Sony par exemple ainsi que les graveurs utilisant les nouvelles interfaces SCSI-3/MMC on besoin d'un mode d'adressage des donnes audio de type little-endian, alors que les autres ont besoin que les donnes audio soit de type big-endian (rseau) normalement utiliser par le protocole SCSI. L'ordre d'adressage des donnes audio sera automatiquement dtect. La seule condition qui ncessite de valider cette option sera dans le cas d'un flux de donnes Intel (little-endian).

Ignorer la taille du mdia peut tre valide si vous souhaitez passez outre la taille connue du mdia. Cette option doit tre utilise avec prcaution. Cette option implique un overburning.

L'option Positionner le drapeau "SCSI IMMED" va imposer un retour immdiat d'une commande SCSI pendant que l'action se droule en arrire plan. Le bus SCSI sera ainsi disponible pour les autres priphriques qui s'y trouvent, ce qui vitera au systme de se figer si le graveur ne rpond pas immdiatement. Ceci peut tre utile sur des vieux systmes utilisant un disque dur ATAPI et un graveur sur le mme bus, ou sur un systme SCSI qui ne supporte pas le mode connect/dconnect. Ces systmes se figerons lors de l'effacement ou la cloture d'un disque, ou lors du remplissage de la session avec la quantit mini de donnes. Notez que tous les graveurs supportent le drapeau IMMED.

Yamaha Audio Master Q. R. est une fonctionnalit qui permet de crer des disques audio de haute qualit avec moins de problmes de lecture dans les platines CD de salon. Sa mise en oeuvre est une variante du mode d'criture SAO, c'est pourquoi vous n'aurez accs cette option seulement si vous avez slectionn le mode d'criture session-at-once. Cette option ne fonctionne pas toutes les vitesses de gravure, et n'autorise la mme quantit de donne qu'en mode standard cause du fait que le sillon de gravure sera largi. Si cette option est valid, un CD de 74 minutes verra sa capacit rduite 63 minutes et un CD de 80 minutes descendra 68 minutes. Cette fonctionnalit fonctionne galement avec les disques de donnes.

L'option Forcespeed mode force le graveur utiliser la vitesse slectionne sans se soucier de la qualit du mdia. Normallement, le graveur est sens connatre la vitesse de gravure maxi autorise en fonction du mdia, et peut rduire la vitesse pour assurer la meilleure qualit de gravure. Utilisez cette option avec prcaution et en connaissance de cause, car habituellement, le graveur sait trs bien quel mdia peut tre grav pleine vitesse.

L'option Plextor VariRec write mode autorise l'utilisateur un lger ajustement de la puissance du laser. Si cette option est configur correctement, cela peut rduire le jitter, ce qui donnera une meilleure qualit sonore, et diminuera les risques d'incompatibilit avec votre lecteur de salon. VariRec ne fonctionnne que si la vtesse de gravure est dfinie x4.

================================================ FILE: doc/french/how_to_use/configuration.html ================================================ Configuration
Pour accder aux options de InfraRecorder, utilisez le menu:
Options Configuration...

Paramtres gnraux

L'option Vrifier si "autorun" est actif chaque dmarrage va interdire l'autorun lorsqu'un CD est insr dans le lecteur/graveur, et que InfraRecorder est lanc. Il est recommand que l'autorun soit inactif, sans quoi, Windows peut lancer des applications qui sont sur le CD alors qu'une gravure est lanc. Ceci peut endommager le CD.

L'option Afficher l'cran de bienvenue au dmarrage affiche l'cran qui vous permet de slectionner le projet que vous souhaitez crer. Si cette option est invalide, le projet Cd de donnes sera slectionn par dfaut.

Les options Associer InfraRecorder aux fichiers .irp, et Associer InfraRecorder avec les images disque si elles sont valides, lancerons automatiquement InfraRecorder avec ces fichiers lorsque vous double-cliquerez sur ce type de fichiers dans l'explorateur Windows.

Si vous voulez que InfraRecorder se rappelle du dernier rpertoire utilis dans la vue explorateur, vous pouvez cocher Se souvenir du dernier dossier actif. Sinon, vous pouvez spcifier un dossier par dfaut utilis chaque dmarrage de InfraRecorder.

L'option Dossier Temporaire vous permet de spcifier l'emplacement du dossier o seront stocker tout les fichiers temporaires de l'application sur votre disque dur comme les images disque par exemple. Si votre disque dur ou votre partition sur laquelle vous stockez ces fichiers temporaires est presque pleine, cela peut tre une bonne ide d'utiliser un autre disque dur pour ce fichier temporaire.

Paramtres avancs

Si vous souhaitez activer la fonctionnalit de journalisation (log), cochez l'option Activer le log. Ceci peut s'avrer utile si vous souhaitez pister un bogue ou une erreur dans InfraRecorder. Il n'est cependant pas souhaitable de laisser le log actif si vous ne souhaitez pas pister d'vnement spcial, car le log ncessite plus de mmoire et de temps CPU.

L'option Activer l'effet de fume valide ou invalide l'affichage d'une colonne de fume durant la gravure. L'effet de fume ncessite l'activation de l'effet Aero dans Windows Vista soit activ. Si Aero n'est pas activ, cette option n'aura aucun effet.

L'option Taille du tampon FIFO permet de chnager la quantit de mmoire RAM utilise pour le tampon en plus de de la taille du buffer physique du graveur. Augmenter la taille du tampon peu permettre d'avoir une gravure plus stable. En rgle gnrale, la taille du FIFO ne doit pas tre infrieure la taille physique du tampon du graveur, et ne doit pas tre suprieure la moiti de la RAM installe sur votre PC. Si vous faites souvent des gravures la vole, vous devez paramtrer une taille importante de tampon FIFO (par exemple 128MiB) pour viter toute rupture (underrun) des donnes lors de la gravure.

Paramtre de langue

Une liste des langues disponible est affiche dans la bote de slection. Pour changer la langue, slectionnez simplement la langue que vous souhaitez, cliquez sur le bouton OK, et redmarrez InfraRecorder. Si la langue que vous souhaitez n'est pas disponible, vrifiez sur le site InfraRecorder si votre langue existe.

Extension

L'extension shell (lorsque elle est active) ajoute une commande supplmentaire au menu contextuel de l'explorateur Windows :

Cela rajoute l'option de graver une image dique, ou un projet InfraRecorder juste en faisant un clic droit sur le fichier au sein de l'explorateur. 

L'extension shell peut tre personnalise pour ajouter les commandes dans un sous-menu. Pour cela, validez l'option Afficher les menus contextuels dans des sous-menus.

On peut aussi personnaliser l'extension shell pour qu'elle n'affiche pas les icnes dans les commandes du menu en invalidant l'option Afficher les icnes dans les menus.

Associer l'Extension Shell

L'extension Shell n'est pas associ automatiquement avec les images disque, et les projet InfraRecorder. Lorsqu'on valide l'option Activer l'extension InfraRecorder, InfraRecorder Informe l'explorateur Windows que d'autres applications peuvent faire appel ces fonctionnalits tendues.

Pour permettre l'exlorateur Windows d'utiliser les fonctionnalits tendues fournies par l'extension shell d'InfraRecorder, l'extension shell doit tre associe avec des types de fichier susceptibles d'utiliser ces fonctionnalits.

Il existe un jeu prdfini d'extensions de fichiers disponible dans la liste. Pour associer l'extension shell d'IInfraRecorder un type de fichier, cochez le type de fichier disponible dans la liste. Vous pouvez rajouter n'importe quel autre type de fichier la liste en cliquant sur le bouton Ajouter une nouvelle extension de fichier la liste :
================================================ FILE: doc/french/how_to_use/copy_audio_disc.html ================================================ Copie de disques audios
Copier un disque audio ncessite plus d'tapes que pour une copie de disque de donnes. Vous devz d'abord sauver les pistes audios sur votre disque dur. Pour cela, ouvrez la boite de dialogue des pistes par le menu :
Actions Grer les pistes...
La fentre devrait tre similaire l'aperu ci-dessous lorsque vous aurez slectionn votre lecteur source et insr un disque audio :
Slectionnez les piste que vous souhaitez sauvegarder (copier) en cliquant sur une piste de dpart, puis une piste de fin en maintenant la touche MAJ enfonc. Lorsque vos piste sont slectionnes, cliquez sur le bouton Enregistrer les pistes slectionnes sur le disque dur :

Il vous sera demand de spcifier le rpertoire de destination pour l'enregistrement des pistes. Slectionnez le rpertoire de votre choix. Lorsque cela est fait, toutes les pistes que vous avez slectionnes seront sauve l'emplacement spcifi (sauf en cas d'erreur de lecture majeur du CD audio).

La prochaine tape consiste crer un projet audio, et d'y ajouter les pistes que vous venez de sauver sur votre disque dur. Pour plus d'informations, consultez cette section.

================================================ FILE: doc/french/how_to_use/copy_data_disc.html ================================================ Copie de disques de donnes

Veuillez noter que cette page contient des informations sur la marche suivre pour copier une CD/DVD de donnes. Si vous souhaitez copier un CD audio (ce qui est une procdure compltement diffrente) rfrez-vous cette section.

Si vous souhaitez copier un disque de donnes, vous avez deux options qui sont : Voulez-vous copier le disque vers un autre disque (par exemple d'un lecteur CD vers un graveur CD) ou vers une image disque sur votre disque dur.

Copier vers un autre disque

Pour copier un disque directement, utilisez le menu :
Actions Copier le disque d'un disque compact...
ou le bouton de la barre d'outil :

Source

Slectionnez le lecteur contenant le CD/DVD que vous souhaitez copier.

Destination

Slectionnez le graveur qui contient le CD/DVD vierge sur lequel sera grav la copie. Si la destination est la mme que la source, vous ne pourrez pas faire de copie la vole.

A la vole

L'criture la vole signifie que les donnes seront lues du lecteur source et crites directement sur le graveur de destination sans passer par un fichier tampon sur votre disque dur (seule une petite quantit de mmoire tampon sera alloue). Si votre lecteur source choue la lecture de certains secteurs de votre disque source, il pourrait ne pas tre capable d'alimenter assez rapidement le graveur de detination, ce qui provoquerait des erreurs d'criture sur le disque de destination. Cependant, la plupart des graveur rcent offre des protections de chute du tampon 0 qui devrait protger le disque de destination si cela devait se produire.

Si l'option A la vole est invalide, une image temporaire du disque sera cre sur votre disque dur. A l'issue de cette opration, l'image disque temporaire sera alors grave sur le disque de destination. Cette opration ncessitera plus d'espace disponible sur votre disque dur, mais sera plus scurisante pour l'criture des donnes.

Cloner le disque

Lorsque cette option est valide, tous les sous-canaux de donnes ainsi que la table d'allocation complte (TOC) du disque source seront galement copis sur le disque cible. Cette option doit tre valide si vous copiez un disque en mode mixte, sans quoi, seule la piste de donnes sera copi. Il est recommand de copier la destination en mode raw96r. Si cette mthode n'est pas supporte par votre graveur, essayez de spcifier une mthode d'criture raw16.

Options de lecture

Les options de lecture sont dcrites dans cette section.

Autres options

Les autres options sont dcrites dans cette section.


Copier vers une image disque

Pour copier un disque dans un fichier image sur votre disque dur, utilisez le menu :
Actions  Copier le disque sur une image disque...

Source

Slectionnez le lecteur source qui contient le CD/DVD que vous souhaitez copier.

Fichier image

Spcifiez l'emplacement et le nom du fichier image. Notez que la taille du fichier qui sera crit sur le disque dur sera de la taille du CD/DVD copier. Vous devez donc vous assurer qu'il y a assez de place sur votre disque dur.

Options de lecture

Les options de lecture sont dcrites dans cette section.

================================================ FILE: doc/french/how_to_use/device_configuration.html ================================================ Configurer les priphriques
Si vous avez fait des modification sur votre matriel, vous aurez probalbement en informer InfraRecorder. Pour afficher la configuration des priphriques d'InfraRecorder, utilisez le menu :
Options Matriel...

Vous verrez alors la liste des priphriques qui ont t dtects par InfraRecorder. Si vous voulez mettre jour la liste des priphrique, cliquez sur le bouton Nouvelle recherche. Cela demandera InfraRecorder d'ffectuer une nouvelle recherche complte sur les priphriques supports sur votre machine.

================================================ FILE: doc/french/how_to_use/disc_information.html ================================================ Les informations du disque
Pour voir les informations dtailles d'un disque insr dans le lecteur/graveur de votre PC, utilisez le menu :
Actions  Information sur le disque <slectionnez le priphrique contenant le disque qui vous intresse>

Champs d'information

Le champ Type de disque affiche le type de disque insr comme par exemple: CD-R, DVD+R DL.

Le champ Type de mdia n'est valide qu'avec un DVD et affiche son "book type", c'est dire, le format physique du DVD (DVD-ROM, DVD-RAM, etc...)

Le champ Rgion affiche pour quelle rgion est encod le DVD. Les numros de rgions sont les suivants :

  1. Etats unis, Canada.
  2. Europe, ainsi que France, Grce, Turquie, Egypte, Arabie, Japon et Afrique du Sud.
  3. Core, Thalande, Vietnam, Borno et Indonsie.
  4. Australie et Nouvelle-Zlande, Mxique, les Caraibes et l'Amerique du Sud.
  5. Inde, Afrique, Russie et pays d'ex URSS.
  6. Rpublique Populaire de Chine.
  7. Inutilis.
  8. Compagnies ariennes et bateaux de croisires.
  9. Etendue (cela correspond souvent un disque dzonn).

Le champ Couche affiche le nombre de couche sur un DVD.

Le champ Pistes affiche le nombre de piste prsentes sur le disque.

Le champ Sessions affiche le nombre de sessions prsentes sur le disque.

Le champ Statut affiche des informations sur le statut du disque et de ces sessions ainsi que l'information si le disque est effaable ou pas.

Le champ Espace utilis affiche la taille de l'espace utilis sur le disque.

Le champ Espace libre affiche la taille de l'espace disponible sur le disque.

================================================ FILE: doc/french/how_to_use/erase_disc.html ================================================ Effacer des disques r-inscriptibles
Pour effacer un disque rinscriptible, vous pouvez soit utiliser le menu :
Actions Effacer/Formatter un disque...
soit par le bouton de la barre d'outils :

Graveur

Slectionnez le graveur dans lequel se trouve le disque effacer.

Mthode d'effacement

Slectionnez une des quatre mthode d'effacement utiliser. La mthode Effacer tout le disque effacera toutes les donnes physiquement prsentes sur le disque. Cette mthode peut tre trs longue. En utilisant la mthode Effacer le disque en mode rapide, seule la table d'allocation (TOC), PMA et le pregap seront effacs. Les donnes effective ne sont pas effaces du disque (mais elle ne seront plus accessible). Au lieu de cela, les donnes seront crases par les donnes que vous crirez sur le disque la prochaine gravure. Cette mthode est beaucoup plus rapide, car elle est effectue le plus souvent en une dizaine de secondes. La mthode Annule la fermeture de la dernire session annule la fermeture de la dernire session (sur un disque multi-session finalis) permettant ainsi de rajouter des sessions sur le disque. La dernire mthode Effacer la dernire session va simplement effacer la dernire session enregistr sur le disque. Le temps d'effacement de la dernire session dpendra de la taille de celle-ci.

Autres options

Si la table d'allocation (TOC) a t endommage sur le disque, InfraRecorder n'effacera pas le disque moins que l'option Ignorer le TOC illgal soit active.

Activer l'option Simulation demandera InfraRecorder d'effectuer l'effacement avec le laser teint. Cette opration est recommand si vous voulez savoir si l'opration se droulera correctement ou pas.

================================================ FILE: doc/french/how_to_use/fixate_disc.html ================================================ Finaliser un disque
Un disque finalis est un disque qu'on peut considr termin. Normallement, un disque est automatiquement finalis aprs l'criture des donnes. Cet outil est utile si les donnes ont t crites mais n'ont, pour quelques raisons que ce soit, pas t finalises. Pour finaliser un disque, utilisez le menu :
Actions Finaliser le disque...

Graveur

Slectionnez le graveur dans lequel se trouve le disque finaliser.

Autres options

Activer l'option Simulation demandera InfraRecorder d'effectuer la finalisation avec le laser teint. Cette opration est recommand si vous voulez savoir si l'opration se droulera correctement ou pas.

================================================ FILE: doc/french/how_to_use/manage_tracks.html ================================================ Grer les pistes
L'outil Grer les pistes affiche les informations de la table d'allocation (TOC) du disque insr dans le lecteur/graveur. Il offre galement la possibilit de vrifier et sauver les pistes slectionnes. Pour ouvrir le gestionnaire de pistes, utilisez le menu :
Actions Grer les pistes...

Slectionnez les piste dsires en cliquant dessus avec la souris en maintenant la touche MAJ ou CTRL appuy. Vous pouvez galement utiliser les flches du clavier et la touche MAJ pour slectionner les pistes dans la liste.

Lorsque vous sauvgardez une piste sur votre disque dur, vous aurez slectionner un dossier de sauvegarde. Les pistes seront alors automatiquement sauves et nommes suivant leur numro et type (Track 1.wav, Track 2.iso).  Pour sauver les pistes slectionnes sur votre disque dur, cliquez sur le bouton Enregistrer les pistes slectionnes sur le disque dur :
Pour rechercher des erreurs sur les pistes slectionnes, utilisez le bouton Rechercher des erreurs sur les pistes slectionnes :

Ci-dessous le rsultat aprs la vrification d'une piste de donnes :.

Vous pouvez galement effacer les pistes slectionnes si votre disque est rinscriptible ne cliquant sur le bouton Effacer les pistes slectionnes du disque :
 

================================================ FILE: doc/french/how_to_use/read_options.html ================================================ Options de lecture

Cette section couvre les options de lecture qui peuvent apparaitre plusieurs moment au sein d'InfraRecorder. Par exemple, lorsque vous souhaitez un disque vers une image ou vers un autre disque.

Bien que ces options puissent apparaitre dans diffrent contextes, elles se prsentent toujours de la mme manire :

Paramtres de lecture

Ignorer les erreurs de lecture

Valider cette option fera en sorte de ne pas abandonner le process en cours si une erreur de lecture de haut niveau est dtecte dans le flux de donnes. Le lecteur/graveur sera galement plac dans un mode ou il ignore toute erreur de lecture dans les secteur de donnes qui rsulte d'un ECC/EDC incorrect.

Lire toutes les donnes sub-channel et toute la TOC

Lorsque cette option est valide, le disque sera lu avec toute les donnes sub-channel et toute la table d'allocation (TOC). Toutes les donnes de la TOC seront places dans un fichier avec le mme nom que le fichier image, mais avec le suffixe .toc.

Vitesse de lecture

Slectionnez la vitesse de lecture du disque. Slectionner l'option Maximum va automatiquement slectionner la vitesse de lecture la plus haute supporte par le lecteur.

Dfinir une vitesse de lecture plus basse peut augmenter la lisibilit du disque.

================================================ FILE: doc/french/how_to_use/working_with_projects/add_boot_image.html ================================================ Ajouter une image de boot

Plusieurs options peuvent tre dfinies lorsque vous ajoutez une image de boot votre projet.

Chemin local

Dans ce champs, vous devez spcifi le chemin local de l'image de boot slectionne. Le chemin est relatif la racine du disque. Par exemple: /boot/ va crer un rpertoire appel boot la racine du disque qui contiendra le fichier slectionn.

Type d'mulation

Cette option vous permet de choisir un type d'mulation pour un disque bootable de type "El Torino". Si l'mulation choisie est de type disquette, la taille du fichier image de boot doit tre exactement la mme que celle d'une disquette de 1200, 1440 ou 2880 Ko. Si l'mulation est de type disque dur, l'image de boot doit imprativement commencer avec un MBR (Section de boot principale du disque) qui contient une seule partition. Si aucune mulation n'est dfinie, le systme chargera et executera l'image de boot sans aucune mulation disque.

Options avances

L'option Faire une image non bootable vous permet d'empcher de booter sur le CD/DVD. Le systme emulera un disque partir l'image de boot sur le CD/DVD, mais bootera sur son disque de boot standard.

Enabling the Write boot-info-table to the image option will cause the boot image to be patched at offset 8 with a 54-byte table containing information about the disc layout. If this option is enabled the local boot image that you have specified will be patched, so make sure that you have a backup of this file if it can't be easily regenerated.

Le champ Segment boot load vous permet de dfinir une adresse de dmarrage (en hexadcimale) dans le cas o aucune mulation pour les disques bootable "El Torito" discs.

Le champ  Taille du boot load vous permet de dfinir le nombre de secteurs virtuels (512 octets) charger dans le cas o aucune mulation n'est dfinie. Il est recommand de charger la totalit du fichier de boot. Certains BIOS sur les cartes mre peuvent avoir des problmes si la taille du boot load n'est pas un multiple de 4.

================================================ FILE: doc/french/how_to_use/working_with_projects/getting_started.html ================================================ Premier projet

Cette section va vous aider dmarrer avec votre premier projet CD/DVD de donne personnalises. InfraRecorder supporte actuellement quatre types de projets.

Les projets CD/DVD de donnes sont utiliss pour crer contenant des fichiers et des rpertoires (en utilisant le systme de fichiers ISO9660) qui peut tre exploit par presque tout ordinateur. Les disques de donnes ne peuvent contenir autant de donnes que les disques audios par secteurs car le systme de fichier stocke galement des donnes de contrle et de corrections d'erreur supplmentaires. De ce fait, les disques de donnes peuvent tre gravs une vitesse plus leves sans perte de donnes ou de qualit. Les disques de donnes peuvent tre gravs en plusieurs fois, autorisant ainsi l'ajout de donnes sur un CD/DVD dj grav. Rfrez-vous cette section pour en savoir plus sur ce sujet.

Les projets CD Audio sont utiliss pour crer des disque audios qui peuvent tre lu par n'importe quelle platine CD de salon (ou d'ordinateur). Les CD audios doivent normalement tre grav une vitesse plus lente que les CD de donnes car ils ne contiennent pas d'informations de contrle ou de correction d'erreurs.

Les projets CD en mode mixte sont utilis pour crer des CD qui contiennent des donnes sur leur premire piste avec les mmes fonctionnalits qu'un CD de donnes, suivi  par des piste audios.Un CD mixte sera lu par n'importe quelle platine de salon, mais la premire piste (celle des donnes) ne sera que du bruit . Les pistes audios seront joues normalement.

Les projets DVD vido sont utiliss pour crer des DVD qui pourront tre lu sur une platine DVD de salon. Des restrictions d'ordre matrielles peuvent cependant empcher la platine de lire un DVD grav suivant le type de DVD grav (+R, +RW, -R, -RW). Renseignez vous sur votre platine de salon avant de graver un DVD vido.

Pour crer un nouveau projet, utilisez le menu:
Fichier Nouveau Projet <slectionnez le type de projet que vous souhaitez crer>
Pour ouvrir un projet existant, utilisez le menu:
File Ouvrir un project...
ou le bouton de la barre d'outils:

Un projet InfraRecorder peut tre directement grav sur un CD/DVD physique, ou tre enregist dans un fichier image disque. Une image disque est un fichier contenant toutes les donnes ajoutes au projet (sauf les pistes audios dans le cas d'un projet audio ou projet mode mixte). Une image disque peut tre graves sur un CD/DVD plus tard. Voir cette section pour plus d'information.

Pour graver votre projet sur un CD/DVD, vous pouvez utiliser le menu:
Actions Graver la compilation D'un disque compact...
ou le bouton de la barre d'outils:

Une description dtaille des options disponible apparat dans cette section.

Environment

General

La barre d'outil de la Vue Explorateur permet de naviguer dans la vue, et d'ajouter au projet les fichiers ou dossier slectionns dans la liste.
La barre d'outil de la vue  Organisation du disque est utilise pour grer le projet et naviguer dans le projet.

Gestion des fichiers

Le menu Edition est utilis pour la gestion des fichiers du projet.
Les options disponibles dans le menu d'dition (ci-dessus) peuvent tre appel partir de la vue de l'explorateur par appel d'un menu contextuel l'aide d'un clic droit dans la vue. Par exemple, si vous faites un clic droit sur un dossier, ce menu apparatra:
Si vous ajoutez votre projet plus de donnes que le mdia slectionn ne peut en contenir, l'indicateur d'espace en bas de la vue passera au rouge:
L'indicateur d'espace passera l'orange si la somme des donnes du projet excde la taille officielle du mdia, mais pourront probablement tenir si l'option Autoriser l'overburning est active:

Vous pouvez changer la taille de l'indicateur afin de correspondre au disque vierge sur lequel vous allez graver votre projet. Pour cela, faites un clic droit sur l'indicateur, et slectionnez le type de mdia appropri.


Gestion de fichiers

Ajout de fichiers

Il y a diffrents moyens d'ajouter des fichiers votre projet. Vous pouvez faire un glisser-dposer depuis la vue explorateur ou depuis l'explorateur Windows vers la vue organisation du disque.  Vous pouvez galement naviguer dans la vue explorateur et slectionner les fichiers que vous souhaitez ajouter votre projet.

Lorsque les fichiers dsirs sont slectionns, vous pouvez utiliser le menu:
Edition Ajouter Slectionn
ou le bouton de la barre d'outil de la vue explorateur:

Vous pouvez galement naviguer dans la vue explorateur sur un dossier, et rapidement ajouter tous les dossiers et fichiers contenus dans ce dossier votre projet.

Pour ajouter tous les fichiers et dossiers dans la vue explorateur active, utilisez le menu:
Edition Ajouter Tout
ou le bouton de la barre d'outil de la vue explorateur:

Supprimer des fichiers

Il y a plusieurs faons de supprimer des fichiers et des dossiers de votre projet. Une faon consiste slectionner les fichiers et dossiers dans la vue organisation du disque et appuyer sur le touche "suppr" de votre clavier. Vous pouvez galement utiliser le menu ou le bouton de la barre d'outil:

Pour supprimer les fichiers slectionns en utilisant le menu:
Edition Supprimer
ou le bouton de la barre d'outil de la vue organisation du disque:

Autres oprations

Pour renommer un fichier ou un dossier slectionn, utilisez le menu:
Edition Renommer
ou le bouton de la barre d'outil de la vue organisation du disque:
Pour ajouter un dossier vide votre projet, utilisez le menu:
Edition Nouveau Dossier
ou le bouton de la barre d'outil de la vue organisation du disque:
================================================ FILE: doc/french/how_to_use/working_with_projects/multisession_disc.html ================================================ Disques multi-sessions

Un disque multi-session est un disque contenant de multiple gravures. Un disque multi-session peut tre graver en plusieurs tapes en ne gravant qu'une session la fois.

Cration d'un nouveau disque multi-session

La cration d'un disque multi-session est simple. Tout d'abord, crez un nouveau projet de donnes:
Fichier Nouveau projet CD(ou DVD) de donnes
Ouvrez les proprits du projet:
Fichier Proprits du projet...
Selectionnez l'onglet ISO, et changez le Format en:
Mode 2 XA (multi-session)

Vous pouvez prsent ajouter des fichiers et des dossiers votre projet normalement. Reportez-vous cette section pour plus d'informations sur la faon de travailler en projet.

Continuer un disque multi-session

Pour ajouter des donnes un disque multi-session dj grav, vous devez d'abord importer les sessions existantes sur le disque. Pour cela, utilisez le menu:
Actions Importer une session...

Une fentre vous permettant de slectionner le priphrique et de voir l'espace allou et disponible sur le disque va s'ouvrir. Si le bouton OK est gris, cela signifie que les sessions du disque prsent dans le priphrique ne peuvent tre importes.

Lorsque vous avez selectionn le priphrique contenant un disque multi-session importer, cliquez sur le bouton OK, et toutes les donnes sur le disque vont tre ajoutes votre projet. Les donnes importes ne peuvent tre manipules ou retires du disque. Tous les fichiers et dossiers imports apparaissent avec un texte gris.

Ds que votre travail sur la nouvelle session est termin et que vous souhaitez ajouter ces donnes au disque, vous pouvez soit utiliser le menu:
Actions Graver la compilation d'un disque compact...
soit le bouton de la barre d'outils:

Ce qu'il faut savoir de plus sur les disques multi-sessions

En plus des donnes que vous allez graver, chaque session ncessite 13Mo supplmentaire pour ces informations. Cela implique que la capacit d'un disque va dpendre du nombre de session qui y sont stockes.

Certains lecteurs de CD/DVD peuvent ne pas reconnaitre les sessions qui se trouvent aprs la premire session d'un disque. Si cela se produit, on peut retrouver ces informations en finalisant un disque. Mais on perd dans ce cas la possibilit d'ajouter de nouvelles sessions au disque.


================================================ FILE: doc/french/how_to_use/working_with_projects/project_settings.html ================================================ Paramtres projet
Cette section traite des paramtres du projet accessible par le menu:
Fichier Proprits du projet...

Paramtres gnraux

Le seul paramtre gnral susceptible d'tre modifi est l'tiquette du disque. L'tiquette soumise par dfaut est base sur la date et l'heure de cration du projet. Notez que le nom de l'tiquette est soumis au mme restriction que celui des fichiers du projet (voir la section Paramtres ISO ci-dessous).

Paramtres ISO

Niveau

Cette option dfinit le niveau de conformit la norme ISO qui dfinit la restriction sur le nom des fichier. Il y a trois niveau de restriction grs par InfraRecorder:

  1. Le niveau 1 utilise des noms de fichier en format 8.3 (huit caractres avec trois caractres pour l'extension), en majuscule, chiffres et caractre soulign(underscore). Le nombre maximum de dossiers dans un chemin est de huit.
  2. Le niveau 2 autorise des noms de fichiers jusqu' 31 caractres.
  3. Le niveau 3 autorise la fragmentation des fichiers (principalement pour l'criture par paquets, ou une gravure incrmentale).
  4. Le niveau 4 n'existe pas vraiment, mais lorsqu'il est slectionn, la norme ISO-9660:1999 (qui est la norme ISO-9660 version 2) est utilise. Cette norme autorise des noms de fichier jusqu' 207 caractres, et la profondeur des chemins peut tre suprieure huit.

Format

Cette option spcifie le format utilis lorsqu'on grave un projet de disque de donnes. Le Mode 1  is normally used when creating regular non multi-session discs while Mode 2 should be used when creating multi-session discs. Mode 1 allows 2048 bytes of data per sector, Mode 2 allows 2336 bytes of data per sector (A CD-ROM sector is 2352 bytes large).

Autres Options

L'option Utiliser les extensions de nom de fichier Joliet ajoute des enregistrements de dossier Joliet dans le disque en plus du standard de nom de fichier ISO9660. L'extension Joliet est communment utilise sur les sytmes Windows, et permet des nom de fichier en format unicode avec une longueur maximum de 64 caractres.

Si cependant, vous souhaitez utiliser des nom de fichiers plus longs, validez l'option Autoriser plus de 64 caractres pour les noms de fichier Joliet. Mme si cela n'est pas pleinement compatible avec les spcifications Joliet, cela fonctionne. Le nombre maximum de caractres est alors tendu 103 caractres.

L'option Omettre les numros de version des fichiers ISO9660 est explicite.

Validez l'option Utilser les extensions Rock Ridge afin de gnrer des enrgistrement SUSP et RR utilisant le protocole Rock Ridge qui dcrit en dtail les fichiers du systme de fichiers ISO9660.

Champs

Cette section contient des champs qui permettent de saisir les informations sur les personnes qui ont cres le projet du CD/DVD. Les champs Editeur, Preparateur, Systme et Ensemble de Volumes peuvent diter directement, les autres champs contiennent souvent des nom de fichiers, ce qui limite leur longueur 36 caractres.

Audio

Cette section permet de crer des information CD-Text. Le CD-Text est un format qui peut tre support par certain lecteur CD audio, et qui permet d'afficher le nom de l'artiste et des chansons lorsque le disque est en lecture. Ces option ne sont valable que dans les projets en mode audio ou en mode mixte.

Boot

Cette section n'est disponible que dans les projets de donnes, et vous permet de spcifier jusqu' 63 images de boot qui pourront tre utilises pour crer un CD/DVD bootable "El Torito". Pour ajouter une image de boot au projet, cliquez sur le bouton Ajouter une nouvelle image de boot au projet :
Rfrez-vous la section Ajouter une image de boot pour plus d'information.
================================================ FILE: doc/french/infra_recorder/acknowledgments.html ================================================ Accords

InfraRecorder utilise des icnes et des des travaux drivs issus du Tango Icon Project. Les travaux drivs bass sur les icnes Tango peuvent tre tlchargs sparment  (sous Creative Commons Attribution Share-Alike license) partir du site web officiel de InfraRecorder.

================================================ FILE: doc/french/infra_recorder/copyright.html ================================================ Copyright

InfraRecorder copyright 2006-2009 Christian Kindahl.

InfraRecorder fonctionne en co-operation avec les logiciels suivant:

================================================ FILE: doc/french/infra_recorder/faq.html ================================================ Foire aux Questions

Pour une liste de questions plus jour, visitez le site http://infrarecorder.org.

InfraRecorder ne reconnait pas mon graveur. Comment puis-je rsoudre le problme ?
Il s'agit bien souvent d'un problme de permission. Par dfaut, InfraRecorder utilise une interface appele SPTI pour accder aux pripharique de gravure. Avec Windows 200, XP et 2003, une permission administrateur est requise pour accder aux priphriques SPTI.

Si vous souhaitez autoriser aux comptes restreints l'accs au priphriques SPTI, vous devez procder comme suit en tant administrateur :

  1. A partir du menu "Dmarrer" appelez la commande "Executer".
  2. Tapez la commande "secpol.msc" (sans les guillemets) et cliquez sur le bouton OK.
  3. Naviguez dans "Stratgies locale" puis "Options de scurit".
  4. Changez la stratgie "Priphrique : ne permettre l'accs au CD-ROM qu'aux utilisateurs connects localement" de "Dsactiv" en "Activ".

Notez que certaines versions de Windows (comme Windows XP par exemple) n'ont pas de gestionnaire de stratgie "secpol.msc". Dans ce cas, vous devrez procder comme suit en tant qu'administrateur :

  1. A partir du menu "Dmarrer" appelez la commande "Executer".
  2. Tapez la commande "regedit" (sans les guillemets) et cliquez sur le bouton OK.
  3. Naviguez au sein de l'arborescence "HKEY_LOCAL_MACHINE", "SOFTWARE", "Microsoft", "Windows NT", "CurrentVersion" et "Winlogon" 
  4. Double cliquez sur la valeur de type REG_SZ appele "allocatecdroms", puis rentrez la valeur "1" (sans les guillemets). with the value "1" (without the quotes).  Si la valeur n'existe pas, vous pouvez la crer en cliquant droit, et en suivant le menu "Nouveau>Valeur chane" avec le nom "allocatecdroms", et la valeur "1".
================================================ FILE: doc/french/infra_recorder/feature_overview.html ================================================ Aperu des fonctionnalits

Cette page liste les fonctions essentielles de InfraRecorder.

Fonctions principales

  • Cre des projets de donnes personnelles, musique, et mixte puis les stocker sur un mdia physique ou dans un fichier image.
  • Cre et enregistrer des images de disques.
  • Cre des copies directes de disques, la vole, ou en utilisant une image disque temporaire.
  • Efface des disques r-inscriptibles par le biais de quatre diffrentes mthodes.
  • Importe des donnes de sessions issues d'un disque multi-session et lui rajouter d'autre sessions.
  • Clture les disques (criture d'information en pilogue pour empcher toute rajout de donnes au disque).
  • Recherche des priphriques sur bus SCSI/IDE et collecte des informations dtailles sur leur capacits.
  • Affiche des informations disque dtailles.
  • Lit et sauvegarde des donnes et pistes audios dans des fichiers (wav. et .iso)
  • Balaye les pistes slectionnes la recherche d'erreur.

Environment

  • Interface moderne et paramtrable du type "explorateur Windows".
  • Glisser/dposer de fichiers d'une vue de l'explorateur Windows vers une vue projet.
  • Vues de projets diffrentes suivant le type de projet pour permettre l'utilisateur de travailler plus facilement.
  • ??? Features a separate express application designed to guide the user to the most essential tools as quick and easy as possible.
  • Une interface multilingue pour l'application principale, et l'extension du shell.

Integration dans l'explorateur

S'intgre l'explorateur et ajoute de nouvelles options au menu contextuel.

  • Grave les projets et images disque enregistrs.
  • Ouvre et dite un projet enregistr.
  • Pleinement paramtrable, les commandes peuvent s'afficher dans un sous-menu avec ou sans icnes.
  • L'extension shell peut tre associes avec n'importe quelle type d'extension dfinie par l'utilisateur.
================================================ FILE: doc/french/infra_recorder/installation.html ================================================ Installation

Le logiciel d'installation (installeur) de InfraRecorder support diffrentes options pour des installations spcifiques. Les paramtres suivants peuvent tre passs l'installeur:

/S
Execute l'installeur (ou dsinstalleur) en mode silencieux. Toutes les choix utilisateurs se feront par dfaut moins de dfinir une option supplmentaire. 

/LANGUAGE=<langue>
Dfini la langue qui doit tre utilise par InfraRecorder. Par exemple: "irsetup.exe /S /LANGUAGE=swedish" installera InfraRecorder en mode silencieux avec la langue Sudoise.

================================================ FILE: doc/french/infra_recorder/introduction.html ================================================ Introduction

Bienvenue

Merci d'avoir install InfraRecorder!  InfraRecorder est une solution de gravure CD/DVD gratuite pour Windows.

Navigation rapide

Aperu des fonctionnalits
Accord de licence en Franais
Accord de licence en Anglais (officielle)
Configuration requise
Dmarrage rapide
Copyright
Accords
Quoi de neuf
Installation


================================================ FILE: doc/french/infra_recorder/license_agreement.html ================================================ License Agreement

GNU GENERAL PUBLIC LICENSE

Version 3, 29 June 2007

Copyright 2007 Free Software Foundation, Inc. <http://fsf.org/>

Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed.

Preamble

The GNU General Public License is a free, copyleft license for software and other kinds of works.

The licenses for most software and other practical works are designed to take away your freedom to share and change the works. By contrast, the GNU General Public License is intended to guarantee your freedom to share and change all versions of a program--to make sure it remains free software for all its users. We, the Free Software Foundation, use the GNU General Public License for most of our software; it applies also to any other work released this way by its authors. You can apply it to your programs, too.

When we speak of free software, we are referring to freedom, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for them if you wish), that you receive source code or can get it if you want it, that you can change the software or use pieces of it in new free programs, and that you know you can do these things.

To protect your rights, we need to prevent others from denying you these rights or asking you to surrender the rights. Therefore, you have certain responsibilities if you distribute copies of the software, or if you modify it: responsibilities to respect the freedom of others.

For example, if you distribute copies of such a program, whether gratis or for a fee, you must pass on to the recipients the same freedoms that you received. You must make sure that they, too, receive or can get the source code. And you must show them these terms so they know their rights.

Developers that use the GNU GPL protect your rights with two steps: (1) assert copyright on the software, and (2) offer you this License giving you legal permission to copy, distribute and/or modify it.

For the developers' and authors' protection, the GPL clearly explains that there is no warranty for this free software. For both users' and authors' sake, the GPL requires that modified versions be marked as changed, so that their problems will not be attributed erroneously to authors of previous versions.

Some devices are designed to deny users access to install or run modified versions of the software inside them, although the manufacturer can do so. This is fundamentally incompatible with the aim of protecting users' freedom to change the software. The systematic pattern of such abuse occurs in the area of products for individuals to use, which is precisely where it is most unacceptable. Therefore, we have designed this version of the GPL to prohibit the practice for those products. If such problems arise substantially in other domains, we stand ready to extend this provision to those domains in future versions of the GPL, as needed to protect the freedom of users.

Finally, every program is threatened constantly by software patents. States should not allow patents to restrict development and use of software on general-purpose computers, but in those that do, we wish to avoid the special danger that patents applied to a free program could make it effectively proprietary. To prevent this, the GPL assures that patents cannot be used to render the program non-free.

The precise terms and conditions for copying, distribution and modification follow.

TERMS AND CONDITIONS

0. Definitions.

“This License” refers to version 3 of the GNU General Public License.

“Copyright” also means copyright-like laws that apply to other kinds of works, such as semiconductor masks.

“The Program” refers to any copyrightable work licensed under this License. Each licensee is addressed as “you”. “Licensees” and “recipients” may be individuals or organizations.

To “modify” a work means to copy from or adapt all or part of the work in a fashion requiring copyright permission, other than the making of an exact copy. The resulting work is called a “modified version” of the earlier work or a work “based on” the earlier work.

A “covered work” means either the unmodified Program or a work based on the Program.

To “propagate” a work means to do anything with it that, without permission, would make you directly or secondarily liable for infringement under applicable copyright law, except executing it on a computer or modifying a private copy. Propagation includes copying, distribution (with or without modification), making available to the public, and in some countries other activities as well.

To “convey” a work means any kind of propagation that enables other parties to make or receive copies. Mere interaction with a user through a computer network, with no transfer of a copy, is not conveying.

An interactive user interface displays “Appropriate Legal Notices” to the extent that it includes a convenient and prominently visible feature that (1) displays an appropriate copyright notice, and (2) tells the user that there is no warranty for the work (except to the extent that warranties are provided), that licensees may convey the work under this License, and how to view a copy of this License. If the interface presents a list of user commands or options, such as a menu, a prominent item in the list meets this criterion.

1. Source Code.

The “source code” for a work means the preferred form of the work for making modifications to it. “Object code” means any non-source form of a work.

A “Standard Interface” means an interface that either is an official standard defined by a recognized standards body, or, in the case of interfaces specified for a particular programming language, one that is widely used among developers working in that language.

The “System Libraries” of an executable work include anything, other than the work as a whole, that (a) is included in the normal form of packaging a Major Component, but which is not part of that Major Component, and (b) serves only to enable use of the work with that Major Component, or to implement a Standard Interface for which an implementation is available to the public in source code form. A “Major Component”, in this context, means a major essential component (kernel, window system, and so on) of the specific operating system (if any) on which the executable work runs, or a compiler used to produce the work, or an object code interpreter used to run it.

The “Corresponding Source” for a work in object code form means all the source code needed to generate, install, and (for an executable work) run the object code and to modify the work, including scripts to control those activities. However, it does not include the work's System Libraries, or general-purpose tools or generally available free programs which are used unmodified in performing those activities but which are not part of the work. For example, Corresponding Source includes interface definition files associated with source files for the work, and the source code for shared libraries and dynamically linked subprograms that the work is specifically designed to require, such as by intimate data communication or control flow between those subprograms and other parts of the work.

The Corresponding Source need not include anything that users can regenerate automatically from other parts of the Corresponding Source.

The Corresponding Source for a work in source code form is that same work.

2. Basic Permissions.

All rights granted under this License are granted for the term of copyright on the Program, and are irrevocable provided the stated conditions are met. This License explicitly affirms your unlimited permission to run the unmodified Program. The output from running a covered work is covered by this License only if the output, given its content, constitutes a covered work. This License acknowledges your rights of fair use or other equivalent, as provided by copyright law.

You may make, run and propagate covered works that you do not convey, without conditions so long as your license otherwise remains in force. You may convey covered works to others for the sole purpose of having them make modifications exclusively for you, or provide you with facilities for running those works, provided that you comply with the terms of this License in conveying all material for which you do not control copyright. Those thus making or running the covered works for you must do so exclusively on your behalf, under your direction and control, on terms that prohibit them from making any copies of your copyrighted material outside their relationship with you.

Conveying under any other circumstances is permitted solely under the conditions stated below. Sublicensing is not allowed; section 10 makes it unnecessary.

3. Protecting Users' Legal Rights From Anti-Circumvention Law.

No covered work shall be deemed part of an effective technological measure under any applicable law fulfilling obligations under article 11 of the WIPO copyright treaty adopted on 20 December 1996, or similar laws prohibiting or restricting circumvention of such measures.

When you convey a covered work, you waive any legal power to forbid circumvention of technological measures to the extent such circumvention is effected by exercising rights under this License with respect to the covered work, and you disclaim any intention to limit operation or modification of the work as a means of enforcing, against the work's users, your or third parties' legal rights to forbid circumvention of technological measures.

4. Conveying Verbatim Copies.

You may convey verbatim copies of the Program's source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice; keep intact all notices stating that this License and any non-permissive terms added in accord with section 7 apply to the code; keep intact all notices of the absence of any warranty; and give all recipients a copy of this License along with the Program.

You may charge any price or no price for each copy that you convey, and you may offer support or warranty protection for a fee.

5. Conveying Modified Source Versions.

You may convey a work based on the Program, or the modifications to produce it from the Program, in the form of source code under the terms of section 4, provided that you also meet all of these conditions:

  • a) The work must carry prominent notices stating that you modified it, and giving a relevant date.
  • b) The work must carry prominent notices stating that it is released under this License and any conditions added under section 7. This requirement modifies the requirement in section 4 to “keep intact all notices”.
  • c) You must license the entire work, as a whole, under this License to anyone who comes into possession of a copy. This License will therefore apply, along with any applicable section 7 additional terms, to the whole of the work, and all its parts, regardless of how they are packaged. This License gives no permission to license the work in any other way, but it does not invalidate such permission if you have separately received it.
  • d) If the work has interactive user interfaces, each must display Appropriate Legal Notices; however, if the Program has interactive interfaces that do not display Appropriate Legal Notices, your work need not make them do so.

A compilation of a covered work with other separate and independent works, which are not by their nature extensions of the covered work, and which are not combined with it such as to form a larger program, in or on a volume of a storage or distribution medium, is called an “aggregate” if the compilation and its resulting copyright are not used to limit the access or legal rights of the compilation's users beyond what the individual works permit. Inclusion of a covered work in an aggregate does not cause this License to apply to the other parts of the aggregate.

6. Conveying Non-Source Forms.

You may convey a covered work in object code form under the terms of sections 4 and 5, provided that you also convey the machine-readable Corresponding Source under the terms of this License, in one of these ways:

  • a) Convey the object code in, or embodied in, a physical product (including a physical distribution medium), accompanied by the Corresponding Source fixed on a durable physical medium customarily used for software interchange.
  • b) Convey the object code in, or embodied in, a physical product (including a physical distribution medium), accompanied by a written offer, valid for at least three years and valid for as long as you offer spare parts or customer support for that product model, to give anyone who possesses the object code either (1) a copy of the Corresponding Source for all the software in the product that is covered by this License, on a durable physical medium customarily used for software interchange, for a price no more than your reasonable cost of physically performing this conveying of source, or (2) access to copy the Corresponding Source from a network server at no charge.
  • c) Convey individual copies of the object code with a copy of the written offer to provide the Corresponding Source. This alternative is allowed only occasionally and noncommercially, and only if you received the object code with such an offer, in accord with subsection 6b.
  • d) Convey the object code by offering access from a designated place (gratis or for a charge), and offer equivalent access to the Corresponding Source in the same way through the same place at no further charge. You need not require recipients to copy the Corresponding Source along with the object code. If the place to copy the object code is a network server, the Corresponding Source may be on a different server (operated by you or a third party) that supports equivalent copying facilities, provided you maintain clear directions next to the object code saying where to find the Corresponding Source. Regardless of what server hosts the Corresponding Source, you remain obligated to ensure that it is available for as long as needed to satisfy these requirements.
  • e) Convey the object code using peer-to-peer transmission, provided you inform other peers where the object code and Corresponding Source of the work are being offered to the general public at no charge under subsection 6d.

A separable portion of the object code, whose source code is excluded from the Corresponding Source as a System Library, need not be included in conveying the object code work.

A “User Product” is either (1) a “consumer product”, which means any tangible personal property which is normally used for personal, family, or household purposes, or (2) anything designed or sold for incorporation into a dwelling. In determining whether a product is a consumer product, doubtful cases shall be resolved in favor of coverage. For a particular product received by a particular user, “normally used” refers to a typical or common use of that class of product, regardless of the status of the particular user or of the way in which the particular user actually uses, or expects or is expected to use, the product. A product is a consumer product regardless of whether the product has substantial commercial, industrial or non-consumer uses, unless such uses represent the only significant mode of use of the product.

“Installation Information” for a User Product means any methods, procedures, authorization keys, or other information required to install and execute modified versions of a covered work in that User Product from a modified version of its Corresponding Source. The information must suffice to ensure that the continued functioning of the modified object code is in no case prevented or interfered with solely because modification has been made.

If you convey an object code work under this section in, or with, or specifically for use in, a User Product, and the conveying occurs as part of a transaction in which the right of possession and use of the User Product is transferred to the recipient in perpetuity or for a fixed term (regardless of how the transaction is characterized), the Corresponding Source conveyed under this section must be accompanied by the Installation Information. But this requirement does not apply if neither you nor any third party retains the ability to install modified object code on the User Product (for example, the work has been installed in ROM).

The requirement to provide Installation Information does not include a requirement to continue to provide support service, warranty, or updates for a work that has been modified or installed by the recipient, or for the User Product in which it has been modified or installed. Access to a network may be denied when the modification itself materially and adversely affects the operation of the network or violates the rules and protocols for communication across the network.

Corresponding Source conveyed, and Installation Information provided, in accord with this section must be in a format that is publicly documented (and with an implementation available to the public in source code form), and must require no special password or key for unpacking, reading or copying.

7. Additional Terms.

“Additional permissions” are terms that supplement the terms of this License by making exceptions from one or more of its conditions. Additional permissions that are applicable to the entire Program shall be treated as though they were included in this License, to the extent that they are valid under applicable law. If additional permissions apply only to part of the Program, that part may be used separately under those permissions, but the entire Program remains governed by this License without regard to the additional permissions.

When you convey a copy of a covered work, you may at your option remove any additional permissions from that copy, or from any part of it. (Additional permissions may be written to require their own removal in certain cases when you modify the work.) You may place additional permissions on material, added by you to a covered work, for which you have or can give appropriate copyright permission.

Notwithstanding any other provision of this License, for material you add to a covered work, you may (if authorized by the copyright holders of that material) supplement the terms of this License with terms:

  • a) Disclaiming warranty or limiting liability differently from the terms of sections 15 and 16 of this License; or
  • b) Requiring preservation of specified reasonable legal notices or author attributions in that material or in the Appropriate Legal Notices displayed by works containing it; or
  • c) Prohibiting misrepresentation of the origin of that material, or requiring that modified versions of such material be marked in reasonable ways as different from the original version; or
  • d) Limiting the use for publicity purposes of names of licensors or authors of the material; or
  • e) Declining to grant rights under trademark law for use of some trade names, trademarks, or service marks; or
  • f) Requiring indemnification of licensors and authors of that material by anyone who conveys the material (or modified versions of it) with contractual assumptions of liability to the recipient, for any liability that these contractual assumptions directly impose on those licensors and authors.

All other non-permissive additional terms are considered “further restrictions” within the meaning of section 10. If the Program as you received it, or any part of it, contains a notice stating that it is governed by this License along with a term that is a further restriction, you may remove that term. If a license document contains a further restriction but permits relicensing or conveying under this License, you may add to a covered work material governed by the terms of that license document, provided that the further restriction does not survive such relicensing or conveying.

If you add terms to a covered work in accord with this section, you must place, in the relevant source files, a statement of the additional terms that apply to those files, or a notice indicating where to find the applicable terms.

Additional terms, permissive or non-permissive, may be stated in the form of a separately written license, or stated as exceptions; the above requirements apply either way.

8. Termination.

You may not propagate or modify a covered work except as expressly provided under this License. Any attempt otherwise to propagate or modify it is void, and will automatically terminate your rights under this License (including any patent licenses granted under the third paragraph of section 11).

However, if you cease all violation of this License, then your license from a particular copyright holder is reinstated (a) provisionally, unless and until the copyright holder explicitly and finally terminates your license, and (b) permanently, if the copyright holder fails to notify you of the violation by some reasonable means prior to 60 days after the cessation.

Moreover, your license from a particular copyright holder is reinstated permanently if the copyright holder notifies you of the violation by some reasonable means, this is the first time you have received notice of violation of this License (for any work) from that copyright holder, and you cure the violation prior to 30 days after your receipt of the notice.

Termination of your rights under this section does not terminate the licenses of parties who have received copies or rights from you under this License. If your rights have been terminated and not permanently reinstated, you do not qualify to receive new licenses for the same material under section 10.

9. Acceptance Not Required for Having Copies.

You are not required to accept this License in order to receive or run a copy of the Program. Ancillary propagation of a covered work occurring solely as a consequence of using peer-to-peer transmission to receive a copy likewise does not require acceptance. However, nothing other than this License grants you permission to propagate or modify any covered work. These actions infringe copyright if you do not accept this License. Therefore, by modifying or propagating a covered work, you indicate your acceptance of this License to do so.

10. Automatic Licensing of Downstream Recipients.

Each time you convey a covered work, the recipient automatically receives a license from the original licensors, to run, modify and propagate that work, subject to this License. You are not responsible for enforcing compliance by third parties with this License.

An “entity transaction” is a transaction transferring control of an organization, or substantially all assets of one, or subdividing an organization, or merging organizations. If propagation of a covered work results from an entity transaction, each party to that transaction who receives a copy of the work also receives whatever licenses to the work the party's predecessor in interest had or could give under the previous paragraph, plus a right to possession of the Corresponding Source of the work from the predecessor in interest, if the predecessor has it or can get it with reasonable efforts.

You may not impose any further restrictions on the exercise of the rights granted or affirmed under this License. For example, you may not impose a license fee, royalty, or other charge for exercise of rights granted under this License, and you may not initiate litigation (including a cross-claim or counterclaim in a lawsuit) alleging that any patent claim is infringed by making, using, selling, offering for sale, or importing the Program or any portion of it.

11. Patents.

A “contributor” is a copyright holder who authorizes use under this License of the Program or a work on which the Program is based. The work thus licensed is called the contributor's “contributor version”.

A contributor's “essential patent claims” are all patent claims owned or controlled by the contributor, whether already acquired or hereafter acquired, that would be infringed by some manner, permitted by this License, of making, using, or selling its contributor version, but do not include claims that would be infringed only as a consequence of further modification of the contributor version. For purposes of this definition, “control” includes the right to grant patent sublicenses in a manner consistent with the requirements of this License.

Each contributor grants you a non-exclusive, worldwide, royalty-free patent license under the contributor's essential patent claims, to make, use, sell, offer for sale, import and otherwise run, modify and propagate the contents of its contributor version.

In the following three paragraphs, a “patent license” is any express agreement or commitment, however denominated, not to enforce a patent (such as an express permission to practice a patent or covenant not to sue for patent infringement). To “grant” such a patent license to a party means to make such an agreement or commitment not to enforce a patent against the party.

If you convey a covered work, knowingly relying on a patent license, and the Corresponding Source of the work is not available for anyone to copy, free of charge and under the terms of this License, through a publicly available network server or other readily accessible means, then you must either (1) cause the Corresponding Source to be so available, or (2) arrange to deprive yourself of the benefit of the patent license for this particular work, or (3) arrange, in a manner consistent with the requirements of this License, to extend the patent license to downstream recipients. “Knowingly relying” means you have actual knowledge that, but for the patent license, your conveying the covered work in a country, or your recipient's use of the covered work in a country, would infringe one or more identifiable patents in that country that you have reason to believe are valid.

If, pursuant to or in connection with a single transaction or arrangement, you convey, or propagate by procuring conveyance of, a covered work, and grant a patent license to some of the parties receiving the covered work authorizing them to use, propagate, modify or convey a specific copy of the covered work, then the patent license you grant is automatically extended to all recipients of the covered work and works based on it.

A patent license is “discriminatory” if it does not include within the scope of its coverage, prohibits the exercise of, or is conditioned on the non-exercise of one or more of the rights that are specifically granted under this License. You may not convey a covered work if you are a party to an arrangement with a third party that is in the business of distributing software, under which you make payment to the third party based on the extent of your activity of conveying the work, and under which the third party grants, to any of the parties who would receive the covered work from you, a discriminatory patent license (a) in connection with copies of the covered work conveyed by you (or copies made from those copies), or (b) primarily for and in connection with specific products or compilations that contain the covered work, unless you entered into that arrangement, or that patent license was granted, prior to 28 March 2007.

Nothing in this License shall be construed as excluding or limiting any implied license or other defenses to infringement that may otherwise be available to you under applicable patent law.

12. No Surrender of Others' Freedom.

If conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot convey a covered work so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not convey it at all. For example, if you agree to terms that obligate you to collect a royalty for further conveying from those to whom you convey the Program, the only way you could satisfy both those terms and this License would be to refrain entirely from conveying the Program.

13. Use with the GNU Affero General Public License.

Notwithstanding any other provision of this License, you have permission to link or combine any covered work with a work licensed under version 3 of the GNU Affero General Public License into a single combined work, and to convey the resulting work. The terms of this License will continue to apply to the part which is the covered work, but the special requirements of the GNU Affero General Public License, section 13, concerning interaction through a network will apply to the combination as such.

14. Revised Versions of this License.

The Free Software Foundation may publish revised and/or new versions of the GNU General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns.

Each version is given a distinguishing version number. If the Program specifies that a certain numbered version of the GNU General Public License “or any later version” applies to it, you have the option of following the terms and conditions either of that numbered version or of any later version published by the Free Software Foundation. If the Program does not specify a version number of the GNU General Public License, you may choose any version ever published by the Free Software Foundation.

If the Program specifies that a proxy can decide which future versions of the GNU General Public License can be used, that proxy's public statement of acceptance of a version permanently authorizes you to choose that version for the Program.

Later license versions may give you additional or different permissions. However, no additional obligations are imposed on any author or copyright holder as a result of your choosing to follow a later version.

15. Disclaimer of Warranty.

THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM “AS IS” WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.

16. Limitation of Liability.

IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.

17. Interpretation of Sections 15 and 16.

If the disclaimer of warranty and limitation of liability provided above cannot be given local legal effect according to their terms, reviewing courts shall apply local law that most closely approximates an absolute waiver of all civil liability in connection with the Program, unless a warranty or assumption of liability accompanies a copy of the Program in return for a fee.

END OF TERMS AND CONDITIONS

How to Apply These Terms to Your New Programs

If you develop a new program, and you want it to be of the greatest possible use to the public, the best way to achieve this is to make it free software which everyone can redistribute and change under these terms.

To do so, attach the following notices to the program. It is safest to attach them to the start of each source file to most effectively state the exclusion of warranty; and each file should have at least the “copyright” line and a pointer to where the full notice is found.

    <one line to give the program's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>

This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.

Also add information on how to contact you by electronic and paper mail.

If the program does terminal interaction, make it output a short notice like this when it starts in an interactive mode:

    <program>  Copyright (C) <year>  <name of author>

This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.

The hypothetical commands `show w' and `show c' should show the appropriate parts of the General Public License. Of course, your program's commands might be different; for a GUI interface, you would use an “about box”.

You should also get your employer (if you work as a programmer) or school, if any, to sign a “copyright disclaimer” for the program, if necessary. For more information on this, and how to apply and follow the GNU GPL, see <http://www.gnu.org/licenses/>.

The GNU General Public License does not permit incorporating your program into proprietary programs. If your program is a subroutine library, you may consider it more useful to permit linking proprietary applications with the library. If this is what you want to do, use the GNU Lesser General Public License instead of this License. But first, please read <http://www.gnu.org/philosophy/why-not-lgpl.html>.

================================================ FILE: doc/french/infra_recorder/license_agreement_fr.html ================================================ Accord de licence

LICENCE PUBLIQUE GNRALE GNU

Version 3, du 29 juin 2007

Copyright 2007 Free Software Foundation, Inc. <http://fsf.org/>

Chacun est autoris copier et distribuer des copies conformes de ce document de licence, mais toute modification en est proscrite.


Traduction franaise par Philippe Verdy, le 30 juin 2007.

Avertissement important au sujet de cette traduction franaise.

Ceci est une traduction en franais de la licence “GNU General Public License” (GPL). Cette traduction est fournie ici dans l’espoir qu’elle facilitera sa comprhension, mais elle ne constitue pas une traduction officielle ou approuve d’un point de vue juridique.

La Free Software Foundation (FSF) ne publie pas cette traduction et ne l’a pas approuve en tant que substitut valide au plan lgal pour la licence authentique “GNU General Public Licence”. Cette traduction n’a pas encore t passe en revue attentivement par un juriste et donc le traducteur ne peut garantir avec certitude qu’elle reprsente avec exactitude la signification lgale des termes de la licence authentique “GNU General Public License” publie en anglais. Cette traduction n’tablit donc lgalement aucun des termes et conditions d’utilisation d’un logiciel sous licence GNU GPL — seul le texte original en anglais le fait. Si vous souhaitez tre sr que les activits que vous projetez seront autorises par la GNU General Public License, veuillez vous rfrer sa seule version anglaise authentique.

La FSF vous recommande fermement de ne pas utiliser cette traduction en tant que termes officiels pour vos propres programmes ; veuillez plutt utiliser la version anglaise authentique telle que publie par la FSF. Si vous choisissez d’acheminer cette traduction en mme temps qu’un Programme sous licence GNU GPL, cela ne vous dispense pas de l’obligation d’acheminer en mme temps une copie de la licence authentique en anglais, et de conserver dans la traduction cet avertissement important en franais et son quivalent en anglais ci-dessous.

Important Warning About This French Translation.
This is a translation of the GNU General Public License (GPL) into French. This translation is distributed in the hope that it will facilitate understanding, but it is not an official or legally approved translation.

The Free Software Foundation (FSF) is not the publisher of this translation and has not approved it as a legal substitute for the authentic GNU General Public License. The translation has not been reviewed carefully by lawyers, and therefore the translator cannot be sure that it exactly represents the legal meaning of the authentic GNU General Public License published in English. This translation does not legally state the terms and conditions of use of any Program licenced under GNU GPL — only the original English text of the GNU LGPL does that. If you wish to be sure whether your planned activities are permitted by the GNU General Public License, please refer to its sole authentic English version.

The FSF strongly urges you not to use this translation as the official distribution terms for your programs; instead, please use the authentic English version published by the FSF. If you choose to convey this translation along with a Program covered by the GPL Licence, this does not remove your obligation to convey at the same time a copy of the authentic GNU GPL License in English, and you must keep in this translation this important warning in English and its equivalent in French above.

Prambule

La Licence Publique Gnrale GNU (“GNU General Public License”) est une licence libre, en “copyleft”, destine aux œuvres logicielles et d’autres types de travaux.

Les licences de la plupart des œuvres logicielles et autres travaux de pratique sont conues pour ter votre libert de partager et modifier ces travaux. En contraste, la Licence  Publique Gnrale GNU a pour but de garantir votre libert de partager et changer toutes les versions d’un programme — afin d’assurer qu’il restera libre pour tous les utilisateurs. Nous, la Free Software Foundation, utilisons la Licence Publique Gnrale GNU pour la plupart de nos logiciels ; cela s’applique aussi tout autre travail dit de cette faon par ses
auteurs. Vous pouvez, vous aussi, l’appliquer vos propres programmes.

Quand nous parlons de logiciel libre (“free”), nous nous rfrons la libert (“freedom”), pas au prix. Nos Licences Publiques Gnrales sont conues pour assurer que vous ayez la libert de distribuer des copies de logiciel libre (et le facturer si vous le souhaitez), que vous receviez le code source ou pouviez l’obtenir si vous le voulez, que vous pouviez modifier le logiciel ou en utiliser toute partie dans de nouveaux logiciels libres, et que vous sachiez que vous avez le droit de faire tout ceci.

Pour protger vos droits, nous avons besoin d’empcher que d’autres vous restreignent ces droits ou vous demande de leur abandonner ces droits. En consquence, vous avez certaines responsabilits si vous distribuez des copies d’un tel programme ou si vous le modifiez : les responsabilits de respecter la libert des autres.

Par exemple, si vous distribuez des copies d’un tel programme, que ce soit gratuit ou contre un paiement, vous devez accorder aux Destinataires les mmes liberts que vous avez reues. Vous devez aussi vous assurer qu’eux aussi reoivent ou peuvent recevoir son code source. Et vous devez leur montrer les termes de cette licence afin qu’ils connaissent leurs droits.

Les dveloppeurs qui utilisent la GPL GNU protgent vos droits en deux tapes : (1) ils affirment leur droits d’auteur (“copyright”) sur le logiciel, et (2) vous accordent cette Licence qui vous donne la permission lgale de le copier, le distribuer et/ou le modifier.

Pour la protection des dveloppeurs et auteurs, la GPL stipule clairement qu’il n’y a pas de garantie pour ce logiciel libre. Aux fins la fois des utilisateurs et auteurs, la GPL require que les versions modifies soient marques comme changes, afin que leurs problmes ne soient pas attribus de faon errone aux auteurs des versions prcdentes.

Certains dispositifs sont conus pour empcher l’accs des utilisateurs l’installation ou l’excution de versions modifies du logiciel l’intrieur de ces dispositifs, alors que les fabricants le peuvent. Ceci est fondamentalement incompatible avec le but de protger la libert des utilisateurs de modifier le logiciel. L’aspect systmatique de tels abus se produit dans le secteur des produits destins aux utilisateurs individuels, ce qui est prcidment ce qui est le plus inacceptable. Aussi, nous avons conu cette version de la GPL pour prohiber cette pratique pour ces produits. Si de tels problmes surviennent dans d’autres domaines, nous nous tenons prt tendre cette restriction ces domaines dans de futures versions de la GPL, autant qu’il sera ncessaire pour protger la libert des utilisateurs.

Finalement, chaque programme est constamment menac par les brevets logiciels. Les tats ne devraient pas autoriser de tels brevets restreindre le dveloppement et l’utilisation de logiciels libres sur des ordinateurs d’usage gnral ; mais dans ceux qui le font, nous voulons spcialement viter le danger que les brevets appliqus un programme libre puisse le rendre effectivement propritaire. Pour empcher ceci, la GPL assure que les brevets ne peuvent tre utiliss pour rendre le programme non-libre.

Les termes prcis et conditions concernant la copie, la distribution et la modification suivent.

TERMES ET CONDITIONS

0. Definitions.

Cette Licence se rfre la version 3 de la “GNU General Public License” (le texte original en anglais).

Droit d’Auteur signifie aussi les droits du “copyright” ou voisins qui s’appliquent d’autres types de travaux, tels que ceux sur les masques de semi-conducteurs.

Le Programme se rfre tout travail qui peut tre sujet au Droit d’Auteur (“copyright”) et dont les droits d’utilisation sont concds en vertu de cette Licence. Chacun des Licencis, qui cette Licence est concde, est dsign par vous. Les Licencis et les Destinataires peuvent tre des personnes physiques ou morales (individus ou organisations).

Modifier un travail signifie en obtenir une copie et adapter tout ou partie du travail d’une faon ncessitant une autorisation d’un titulaire de Droit d’Auteur, autre que celle permettant d’en produire une copie conforme. Le travail rsultant est appel une version modifie du prcdent travail, ou un travail bas sur le prcdent travail.

Un Travail Couvert signifie soit le Programme non modifi soit un travail bas sur le Programme.

Propager un travail signifie faire quoi que ce soit avec lui qui, sans permission, vous rendrait directement ou indirectement responsable d’un dlit de contrefaon suivant les lois relatives au Droit d’Auteur, l’exception de son excution sur un ordinateur ou de la modification d’une copie prive. La propagation inclue la copie, la distribution (avec ou sans modification), la mise disposition envers le public, et aussi d'autres activits dans certains pays.

Acheminer un travail signifie tout moyen de propagation de celui-ci qui permet d’autres parties de raliser ou recevoir des copies. La simple interaction d’un utilisateur  travers un rseau informatique, sans transfert effectif d’une copie, ne constitue pas un acheminement.

Une interface utilisateur interactive affiche des Notices Lgales Appropries quand elle comprend un dispositif convenable, bien visible et vident qui (1) affiche une notice approprie sur les droits d’auteur et (2) informe l’utilisateur qu’il n’y a pas de garantie pour le travail (sauf si des garanties ont t fournies hors du cadre de cette Licence), que les licencis peuvent acheminer le travail sous cette Licence, et comment voir une copie de cette Licence. Si l’interface prsente une liste de commandes utilisateur ou d’options, tel qu’un menu, un lment vident dans la liste prsente remplit ce critre.

1. Code source.

Le code source d’un travail signifie la forme prfre du travail permettant ou facilitant les modifications de celui-ci. Le code objet d’un travail signifie toute forme du travail qui n’en est pas le code source.

Une Interface Standard signifie une interface qui est soit celle d’une norme officielle dfinie par un organisme de normalisation reconnu ou, dans le cas des interfaces spcifies pour un langage de programmation particulier, une interface largement utilise parmi les dveloppeurs travaillant dans ce langage.

Les Bibliothques Systme d’un travail excutable incluent tout ce qui, en dehors du travail dans son ensemble, (a) est inclus dans la forme usuelle de paquetage d’un Composant Majeur mais ne fait pas partie de ce Composant Majeur et (b) sert seulement permettre l’utilisation du travail avec ce Composant Majeur ou implmenter une Interface Standard pour laquelle une implmentation est disponible au public sous forme de code source ; un Composant Majeur signifie, dans ce contexte, un composant majeur essentiel (noyau, systme de fentrage, etc.) du systme d’exploitation (le cas chant) d’un systme sur lequel le travail excutable fonctionne, ou bien un compilateur utilis pour produire le code objet du travail, ou un interprte de code objet utilis pour excuter celui-ci.

Le Source Correspondant d’un travail sous forme de code objet signifie l’ensemble des codes sources ncessaires pour gnrer, installer et (dans le cas d’un travail excutable) excuter le code objet et modifier le travail, y compris les scripts pour contrler ces activits. Cependant, cela n’inclue pas les Bibliothques Systme du travail, ni les outils d’usage gnral ou les programmes libres gnralement disponibles qui peuvent tre utiliss sans modification pour achever ces activits mais ne sont pas partie de ce travail. Par exemple le Source Correspondant inclut les fichiers de dfinition d’interfaces associs aux fichiers sources du travail, et le code source des bibliothques partages et des sous-routines lies
dynamiquement, pour lesquelles le travail est spcifiquement conu pour les requrir via, par exemple, des communications de donnes ou contrles de flux internes entre ces sous-programmes et d’autres parties du travail.

Le Source Correspondant n’a pas besoin d’inclure tout ce que les utilisateurs peuvent regnrer automatiquement partir d’autres parties du Source Correspondant.
Le Source Correspondant pour un travail sous forme de code source est ce mme travail.

2. Permissions de base.

Tous les droits accords suivant cette Licence le sont jusqu’au terme des Droits d’Auteur (“copyright”) sur le Programme, et sont irrvocables pourvu que les conditions tablies soient remplies. Cette Licence affirme explicitement votre permission illimite d’excuter le Programme non modifi. La sortie produite par l’excution d’un Travail Couvert n’est couverte par cette Licence que si cette sortie, tant donn leur contenu, constitue un Travail Couvert. Cette Licence reconnait vos propres droits d’usage raisonnable (“fair use” en
lgislation des tats-Unis d’Amrique) ou autres quivalents, tels qu’ils sont pourvus par la loi applicable sur le Droit d’Auteur (“copyright”).

Vous pouvez crer, excuter et propager sans condition des Travaux Couverts que vous n’acheminez pas, aussi longtemps que votre licence demeure en vigueur. Vous pouvez acheminer des Travaux Couverts d’autres personnes dans le seul but de leur faire raliser des modifications votre usage exclusif, ou pour qu’ils vous fournissent des facilits vous permettant d’excuter ces travaux, pourvu que vous vous conformiez aux termes de cette Licence lors de l’acheminement de tout matriel dont vous ne contrlez pas le Droit d’Auteur (“copyright”). Ceux qui, ds lors, ralisent ou excutent pour vous les Travaux Couverts ne doivent alors le faire qu’exclusivement pour votre propre compte, sous votre direction et votre contrle, suivant des termes qui leur interdisent de raliser, en dehors de leurs relations avec vous, toute copie de votre matriel soumis au Droit d’Auteur.

L’acheminement dans toutes les autres circonstances n’est permis que selon les conditions tablies ci-dessous. La concession de sous-licences n’est pas autoris ; l’article 10 rend cet usage non ncessaire.

3. Protection des droits lgaux des utilisateurs envers les lois anti-contournement.

Aucun Travail Couvert ne doit tre vu comme faisant partie d’une mesure technologique effective selon toute loi applicable remplissant les obligations prvues l’article 11 du trait international sur le droit d’auteur adopt l’OMPI le 20 dcembre 1996, ou toutes lois similaires qui prohibent ou restreignent le contournement de telles mesures.

Si vous acheminez un Travail Couvert, vous renoncez tout pouvoir lgal d’interdire le contournement des mesures technologiques dans tous les cas o un tel contournement serait effectu en exerant les droits prvus dans cette Licence pour ce Travail Couvert, et vous dclarez rejeter toute intention de limiter l’opration ou la modification du Travail, en tant que moyens de renforcer, l’encontre des utilisateurs de ce Travail, vos droits lgaux ou ceux de tierces parties d’interdire le contournement des mesures technologiques.

4. Acheminement des copies conformes.

Vous pouvez acheminer des copies conformes du code source du Programme tel que vous l’avez reu, sur n’importe quel support, pourvu que vous publiiez scrupuleusement et de faon approprie sur chaque copie une notice de Droit d’Auteur approprie ; gardez intactes toutes les notices tablissant que cette Licence et tous les termes additionnels non permissifs ajouts en accord avec l’article 7 s’appliquent ce code ; et donnez chacun des Destinataires une copie de cette Licence en mme temps que le Programme.

Vous pouvez facturer un prix quelconque, y compris gratuit, chacune des copies que vous acheminez, et vous pouvez offrir une protection additionnelle de support ou de garantie en change d’un paiement.

5. Acheminement des versions sources modifies.

Vous pouvez acheminer un travail bas sur le Programme, ou bien les modifications pour le produire partir du Programme, sous la forme de code source suivant les termes de l’article 4, pourvu que voussatisfassiez aussi chacune des conditions requises suivantes :

  • a) Le travail doit comporter des notices videntes tablissant que vous l’avez modifi et donnant la date correspondante.
  • b) Le travail doit comporter des notices videntes tablissant qu’il est dit selon cette Licence et les conditions ajoutes d’aprs l’article 7. Cette obligation vient modifier l’obligation de l’article 4 de garder intactes toutes les notices. .
  • c) Vous devez licencier le travail entier, comme un tout, suivant cette Licence quiconque entre en possession d’une copie. Cette Licence s’appliquera en consquence, avec les termes additionnels applicables prvus par l’article 7, la totalit du travail et chacune de ses parties, indpendamment de la faon dont ils sont empaquets. Cette licence ne donne aucune permission de licencier le travail d’une autre faon, mais elle n’invalide pas une telle permission si vous l’avez reue sparment. 
  • d) Si le travail a des interfaces utilisateurs interactives, chacune doit afficher les Notices Lgales Appropries ; cependant si le Programme a des interfaces qui n’affichent pas les Notices Lgales Appropries, votre travail n’a pas les modifier pour qu’elles les affichent. 

Une compilation d’un Travail Couvert avec d’autres travaux spars et indpendants, qui ne sont pas par leur nature des extensions du Travail Couvert, et qui ne sont pas combins avec lui de faon former un programme plus large, dans ou sur un volume de stockage ou un support de distribution, est appel un aggrgat si la compilation et son Droit d’Auteur rsultant ne sont pas utiliss pour limiter l’accs ou les droits lgaux des utilisateurs de la compilation en dea de ce que permettent les travaux individuels. L’inclusion d’un Travail Couvert dans un aggrgat ne cause pas l’application de cette Licence aux autres parties de l’aggrgat.

6. Acheminement des formes non sources.

Vous pouvez acheminer sous forme de code objet un Travail Couvert suivant les termes des articles 4 et 5, pourvu que vous acheminiez galement suivant les termes de cette Licence le Source Correspondantlisible par une machine, d’une des faons suivantes :

  • a) Acheminer le code objet sur, ou inclus dans, un produit physique (y compris un support de distribution physique), accompagn par le Source Correspondant fix sur un support physique durable habituellement utilis pour les changes de logiciels.
  • b) Acheminer le code objet sur, ou inclus dans, un produit physique (y compris un support de distribution physique), accompagn d’une offre crite, valide pour au moins trois annes et valide pour aussi longtemps que vous fournissez des pices de rechange ou un support client pour ce modle de produit, afin de donner quiconque possde le code objet soit (1) une copie du Source Correspondant tout logiciel dans ce produit qui est couvert par cette Licence, sur un support physique durable habituellement utilis pour les changes de logiciels, pour un prix non suprieur au cot raisonnable de la ralisation physique de l’acheminement de la source, ou soit (2) un accs permettant de copier le Source Correspondant depuis un serveur rseau sans frais.
  • c) Acheminer des copies individuelles du code objet avec une copie de l’offre crite de fournir le Source Correspondant. Cette alternative est permise seulement occasionellement et non commercialement, et seulement si vous avez reu le code objet avec une telle offre, en accord avec l’article 6 alina b.
  • d) Acheminer le code objet en offrant un accs depuis un emplacement dsign (gratuit ou contre facturation) et offrir un accs quivalent au Source Correspondant de la mme faon via le mme emplacement et sans facturation supplmentaire. Vous n’avez pas besoin d’obliger les Destinataires copier le Source Correspondant en mme temps que le code objet. Si l’emplacement pour copier le code objet est un serveur rseau, le Source Correspondant peut tre sur un serveur diffrent (opr par vous ou par un tiers) qui supporte des facilits quivalentes de copie, pourvu que vous mainteniez des directions claires  proximit du code objet indiquant o trouver le Source Correspondant. Indpendamment de quel serveur hberge le Source Correspondant, vous restez oblig de vous assurer qu’il reste disponible aussi longtemps que ncessaire pour satisfaire ces obligations.
  • e) Acheminer le code objet en utilisant une transmission d’gal--gal, pourvu que vous informiez les autres participants sur o le code objet et le Source Correspondant du travail sont offerts sans frais au public gnral suivant l’article 6 alina d. Une portion sparable du code objet, dont le code source est exclu du Source Correspondant en tant que Bibliothque Systme, n’a pas besoin d’tre inclu dans l’acheminement du travail sous forme de code objet.

A separable portion of the object code, whose source code is excluded from the Corresponding Source as a System Library, need not be included in conveying the object code work.

Un Produit Utilisateur est soit (1) un Produit de Consommation, ce qui signifie toute proprit personnelle tangible normalement utilise des fins personnelles, familiales ou relatives au foyer, soit (2) toute chose conue ou vendue pour l’incorporation dans un lieu d’habitation. Pour dterminer si un produit constitue un Produit de Consommation, les cas ambigus sont rsolus en fonction de la couverture. Pour un produit particulier reu par un utilisateur particulier, l’expression normalement utilise ci-avant se rfre une utilisation typique ou l’usage commun de produits de mme catgorie, indpendamment du statut de cet utilisateur particulier ou de la faon spcifique dont cet utilisateur particulier utilise effectivement ou s’attend lui-mme ou est attendu utiliser ce produit. Un produit est un Produit de Consommation indpendamment du fait que ce produit a ou n’a pas d’utilisations substantielles commerciales, industrielles ou hors Consommation, moins que de telles utilisations reprsentent le seul mode significatif d’utilisation duproduit.

Les Informations d’Installation d’un Produit Utilisateur signifient toutes les mthodes, procdures, cls d’autorisation ou autres informations requises pour installer et excuter des versions modifies d’un Travail Couvert dans ce Produit Utilisateur partir d’une version modifie de son Source Correspondant. Les informations qui suffisent assurer la continuit de fonctionnement du code objet modifi ne doivent en aucun cas tre empches ou interfres du seul fait qu’unemodification a t effectue.

Si vous acheminez le code objet d’un Travail Couvert dans, ou avec, ou spcifiquement pour l’utilisation dans, un Produit Utilisateur et l’acheminement se produit en tant qu’lment d’une transaction dans laquelle le droit de possession et d’utilisation du Produit Utilisateur est transfr au Destinataire dfinitivement ou pour un terme fix (indpendamment de la faon dont la transaction est caractrise), le Source Correspondant achemin selon cet article-ci doit tre accompagn des Informations d’Installation. Mais cette obligation ne s’applique pas si ni vous ni aucune tierce partie ne dtient la possibilit d’intaller un code objet modifi sur le ProduitUtilisateur (par exemple, le travail a t install en mmoire morte).

L’obligation de fournir les Informations d’Installation n’inclue pas celle de continuer fournir un service de support, une garantie ou des mises jour pour un travail qui a t modifi ou install par le Destinataire, ou pour le Produit Utilisateur dans lequel il a t modifi ou install. L’accs un rseau peut tre rejet quand la modification elle-mme affecte matriellement et dfavorablement les oprations du rseau ou viole les rgles et protocoles de communication au travers du rseau.

Le Source Correspondant achemin et les Informations d’Installation fournies, en accord avec cet article, doivent tre dans un format publiquement document (et dont une implmentation est disponible auprs du public sous forme de code source) et ne doit ncessiter aucune cl ou mot de passe spcial pour le dpaquetage, la lecture oula copie.

7. Termes additionnels.

Les permissions additionelles dsignent les termes qui supplmentent ceux de cette Licence en mettant des exceptions l’une ou plusieurs de ses conditions. Les permissions additionnelles qui sont applicables au Programme entier doivent tre traites comme si elles taient incluent dans cette Licence, dans les limites de leur validit suivant la loi applicable. Si des permissions additionnelles s’appliquent seulement une partie du Programme, cette partie peut tre utilise sparment suivant ces permissions, mais le Programme tout entier reste gouvern par cette Licence sans regard auxpermissions additionelles.

Quand vous acheminez une copie d’un Travail Couvert, vous pouvez votre convenance ter toute permission additionelle de cette copie, ou de n’importe quelle partie de celui-ci. (Des permissions additionnelles peuvent tre rdiges de faon requrir leur propre suppression dans certains cas o vous modifiez le travail.) Vous pouvez placer les permissions additionnelles sur le matriel achemin, ajoutes par vous un Travail Couvert pour lequel vous avez ou pouvezdonner les permissions de Droit d’Auteur (“copyright”) appropries.

Nonobstant toute autre clause de cette Licence, pour tout constituant que vous ajoutez un Travail Couvert, vous pouvez (si autoris par les titulaires de Droit d’Auteur pour ce constituant) supplmenter lestermes de cette Licence avec des termes :

  • a) qui rejettent la garantie ou limitent la responsabilit de faon diffrente des termes des articles 15 et 16 de cette Licence ; ou
  • b) qui requirent la prservation de notices lgales raisonnables spcifies ou les attributions d’auteur dans ce constituant ou dans les Notices Lgales Appropries affiches par les travaux qui le contiennent ; ou
  • c) qui prohibent la reprsentation incorrecte de l’origine de ce constituant, ou qui requirent que les versions modifies d’un tel constituant soit marques par des moyens raisonnables comme diffrentes de la version originale ; ou
  • d) qui limitent l’usage but publicitaire des noms des concdants de licence et des auteurs du constituant ; ou
  • e) qui refusent accorder des droits selon la lgislation relative aux marques commerciales, pour l’utilisation dans des noms commerciaux, marques commerciales ou  arques de services ; ou
  • f) qui requirent l’indemnisation des concdants de licences et auteurs du constituant par quiconque achemine ce constituant (ou des versions modifies de celui-ci) en assumant contractuellement la responsabilit envers le Destinataire, pour toute responsabilit que ces engagements contractuels imposent directement ces octroyants de licences et auteurs.

Tous les autres termes additionnels non permissifs sont considrs comme des restrictions avances dans le sens de l’article 10. Si le Programme tel que vous l’avez reu, ou toute partie de celui-ci, contient une notice tablissant qu’il est gouvern par cette Licence en mme temps qu’un terme qui est une restriction avance, vous pouvez ter ce terme. Si un document de licence contient une restriction avance mais permet la reconcession de licence ou l’acheminement suivant cette Licence, vous pouvez ajouter un Travail Couvert constituant gouvern par les termes de ce document de licence, pourvu que la restriction avance ne survit pas un telle cession de licenceou acheminement.

Si vous ajoutez des termes un Travail Couvert en accord avec cet article, vous devez placer, dans les fichiers sources appropris, une dclaration des termes additionnels qui s’appliquent ces fichiers, ou une notice indiquant o trouver les termes applicables.

Les termes additionnels, qu’ils soient permissifs ou non permissifs, peuvent tre tablis sous la forme d’une licence crite sparment, ou tablis comme des exceptions ; les obligations ci-dessus s’appliquentdans chacun de ces cas.

8. Terminaison.

Vous ne pouvez ni propager ni modifier un Travail Couvert autrement que suivant les termes de cette Licence. Toute autre tentative de le propager ou le modifier est nulle et terminera automatiquement vos droits selon cette Licence (y compris toute licence de brevet accorde selon le troisime paragraphe de l’article 11).

Cependant, si vous cessez toute violation de cette Licence, alors votre licence depuis un titulaire de Droit d’Auteur (“copyright”) est rinstaure (a) titre provisoire moins que et jusqu’ ce que le titulaire de Droit d’Auteur termine finalement et explicitement votre licence, et (b) de faon permanente si le titulaire de Droit d’Auteur ne parvient pas vous notifier de la violation par quelque moyenraisonnable dans les soixante (60) jours aprs la cessation.

De plus, votre licence depuis un titulaire particulier de Droit d’Auteur est rinstaure de faon permanente si ce titulaire vous notifie de la violation par quelque moyen raisonnable, c’est la premire fois que vous avez reu une notification deviolation de cette Licence (pour un travail quelconque) depuis ce titulaire de Droit d’Auteur, et vous rsolvez la violation dans les trente (30) jours quisuivent votre rception de la notification.

La terminaison de vos droits suivant cette section ne terminera pas les licences des parties qui ont reu des copies ou droits de votre part suivant cette Licence. Si vos droits ont t termins et non rinstaurs de faon permanente, vous n’tes plus qualifi recevoirde nouvelles licences pour les mmes constituants selon l’article 10.

9. Acceptation non requise pour obtenir des copies.

Vous n’tes pas oblig d’accepter cette licence afin de recevoir ou excuter une copie du Programme. La propagation asservie d’un Travail Couvert qui se produit simplement en consquence d’une transmission d’gal--gal pour recevoir une copie ne ncessite pas l’acceptation. Cependant, rien d’autre que cette Licence ne vous accorde la permission de propager ou modifier un quelconque Travail Couvert. Ces actions enfreignent le Droit d’Auteur si vous n’acceptez pas cette Licence. Par consquent, en modifiant ou propageant un Travail Couvert,vous indiquez votre acceptation de cette Licence pour agir ainsi.

10. Cession automatique de Licence aux Destinataires et intermdiaires.

Chaque fois que vous acheminez un Travail Couvert, le Destinataire reoit automatiquement une licence depuis les concdants originaux, pour excuter, modifier et propager ce travail, suivant les termes de cette Licence. Vous n’tes pas responsable du renforcement de laconformation des tierces parties avec cette Licence.

Une transaction d’entit dsigne une transaction qui transfre le contrle d’une organisation, ou de substantiellement tous ses actifs, ou la subdivision d’une organisation, ou la fusion de plusieurs organisations. Si la propagation d’un Travail Couvert rsulte d’une transaction d’entit, chaque partie cette transaction qui reoit une copie du travail reoit aussi les licences pour le travail que le prdcesseur intress cette partie avait ou pourrait donner selon le paragraphe prcdent, plus un droit de possession du Source Correspondant de ce travail depuis le prdcesseur intress si ce prdcesseur en dispose ou peut l’obtenir par des efforts raisonnables.

Vous ne pouvez imposer aucune restriction avance dans l’exercice des droits accords ou affirms selon cette Licence. Par exemple, vous ne pouvez imposer aucun paiement pour la licence, aucune royaltie, ni aucune autre charge pour l’exercice des droits accords selon cette Licence ; et vous ne pouvez amorcer aucun litige judiciaire (y compris une rclamation croise ou contre-rclamation dans un procs) sur l’allgation qu’une revendication de brevet est enfreinte par la ralisation, l’utilisation, la vente, l’offre de vente, oul’importation du Programme ou d’une quelconque portion de celui-ci.

11. Brevets.

Un contributeur est un titulaire de Droit d’Auteur (“copyright”) qui autorise l’utilisation selon cette Licence du Programme ou du travail sur lequel le Programme est bas. Le travail ainsi soumis licence est appel la version contributive de ce contributeur.

Les revendications de brevet essentielles sont toutes les revendications de brevets dtenues ou contrles par le contributeur, qu’elles soient dj acquises par lui ou acquises subsquemment, qui pourraient tre enfreintes de quelque manire, permises par cette Licence, sur la ralisation, l’utilisation ou la vente de la version contributive de celui-ci. Aux fins de cette dfinition, le contrle inclue le droit de concder des sous-licences de brevets d’une manire consistante, ncessaire et suffisante, avec les obligations de cette
Licence.

Chaque contributeur vous accorde une licence de brevet non exclusive, mondiale et libre de toute royaltie, selon les revendications de brevet essentielles, pour raliser, utiliser, vendre, offrir la vente, importer et autrement excuter, modifier et propager les contenus de saversion contributive.

Dans les trois paragraphes suivants, une licence de brevet dsigne tous les accords ou engagements exprims, quel que soit le nom que vous lui donnez, de ne pas mettre en vigueur un brevet (telle qu’une permission explicite pour mettre en pratique un brevet, ou un accord pour ne pas poursuivre un Destinataire pour cause de violation de brevet). Accorder une telle licence de brevet une partie signifie conclure un tel accord ou engagement ne pas faire appliquer le brevet cette partie.

Si vous acheminez un Travail Couvert, dpendant en connaissance d’une licence de brevet, et si le Source Correspondant du travail n’est pas disponible quiconque copie, sans frais et suivant les termes de cette Licence, travers un serveur rseau publiquement acessible ou tout autre moyen immdiatement accessible, alors vous devez soit (1) rendre
la Source Correspondante ainsi disponible, soit (2) vous engager vous priver pour vous-mme du bnfice de la licence de brevet pour ce travail particulier, soit (3) vous engager, d’une faon consistante avec les obligations de cette Licence, tendre la licence de brevet aux Destinataires de ce travail. Dpendant en connaissance signifie que vous avez effectivement connaissance que, selon la licence de brevet, votre acheminement du Travail Couvert dans un pays, ou l’utilisation du Travail Couvert par votre Destinataire dans un pays, enfreindrait un ou plusieurs brevets identifiables dans ce pays o vous avez des raisons de penser qu’ils sont valides.

Si, conformment ou en liaison avec une mme transaction ou un mme arrangement, vous acheminez, ou propagez en procurant un acheminement de, un Travail Couvert et accordez une licence de brevet l’une des parties recevant le Travail Couvert pour lui permettre d’utiliser, propager, modifier ou acheminer une copie spcifique du Travail Couvert, alors votre accord est automatiquement tendu tous les Destinataires du Travail Couvert et des travaux bass sur celui-ci.

Une licence de brevet est discriminatoire si, dans le champ de sa couverture, elle n’inclut pas un ou plusieurs des droits qui sont spcifiquement accords selon cette Licence, ou en prohibe l’exercice, ou est conditionne par le non-exercice d’un ou plusieurs de ces droits. Vous ne pouvez pas acheminer un Travail Couvert si vous tes partie un arrangement selon lequel une partie tierce exerant son activit dans la distribution de logiciels et laquelle vous effectuez un paiement fond sur l’tendue de votre activit d’acheminement du travail, et selon lequel la partie tierce accorde, une quelconque partie qui recevrait depuis vous le Travail Couvert, une licence de brevet discriminatoire (a) en relation avec les copies du Travail Couvert achemines par vous (ou les copies ralises partir de ces copies), ou (b) avant tout destine et en relation avec des produits spcifiques ou compilations contenant le Travail Couvert, moins que vous ayez conclu cet arrangement ou que la licence de brevet ait taccorde avant le 28 mars 2007.

Rien dans cette Licence ne devrait tre interprt comme devant exclure ou limiter toute licence implicite ou d’autres moyens de dfense une infraction qui vous seraient autrement disponible selon la loiapplicable relative aux brevets.

12. Non abandon de la libert des autres.

Si des conditions vous sont imposes (que ce soit par dcision judiciaire, par un accord ou autrement) qui contredisent les conditions de cette Licence, elles ne vous excusent pas des conditions de cette Licence. Si vous ne pouvez pas acheminer un Travail Couvert de faon satisfaire simultnment vos obligations suivant cette Licence et toutes autres obligations pertinentes, alors en consquence vous ne pouvez pas du tout l’acheminer. Par exemple, si vous avez un accord sur des termes qui vous obligent collecter pour le racheminement des royalties depuis ceux qui vous acheminez le Programme, la seule faon qui puisse vous permettre de satisfaire la fois ces termes et ceux de cette Licence sera de vous abstenir entirement d’acheminer leProgramme.

13. Utilisation avec la Licence Gnrale Publique Affero GNU.

Nonobstant toute autre clause de cette Licence, vous avez la permission de lier ou combiner tout Travail Couvert avec un travail plac sous la version 3 de la Licence Gnrale Publique GNU Affero (“GNU Affero General Public License”) en un seul travail combin, et d’acheminer le travail rsultant. Les termes de cette Licence continueront s’appliquer la partie formant un Travail Couvert, mais les obligations spciales de la Licence Gnrale Publique GNU Affero, article 13, concernant l’interaction travers un rseau s’appliqueront la combinaison en tant que telle.

14. Versions rvises de cette License.

La Free Software Foundation peut publier des versions rvises et/ou nouvelles de la Licence Publique Gnrale GNU (“GNU General Public License”) de temps en temps. De telles version nouvelles resteront similaires dans l’esprit avec la prsente version, mais peuvent diffrer dans le dtail afin de traiter de nouveaux problmes ouproccupations.

Chaque version reoit un numro de version distinctif. Si le Programme indique qu’une version spcifique de la Licence Publique Gnrale GNU ou toute version ultrieure (“or any later version”) s’applique celui-ci, vous avez le choix de suivre soit les termes et conditions de cette version numrote, soit ceux de n’importe quelle version publie ultrieurement par la Free Software Foundation. Si le Programme n’indique pas une version spcifique de la Licence Publique Gnrale GNU, vous pouvez choisir l’une quelconque des versions qui ont tpublies par la Free Software Foundation.

Si le Programme spcifie qu’un intermdiaire peut dcider quelles versions futures de la Licence Gnrale Publique GNU peut tre utilise, la dclaration publique d’acceptation d’une version par cetintermdiaire vous autorise choisir cette version pour le Programme.

Des versions ultrieures de la licence peuvent vous donner des permissions additionelles ou diffrentes. Cependant aucune obligation additionelle n’est impose l’un des auteurs ou titulaires de Droitd’Auteur du fait de votre choix de suivre une version ultrieure.

15. Dclaration d’absence de garantie.

IL N’Y A AUCUNE GARANTIE POUR LE PROGRAMME, DANS LES LIMITES PERMISES PAR LA LOI APPLICABLE. MOINS QUE CELA NE SOIT TABLI DIFFREMMENT PAR CRIT, LES PROPRITAIRES DE DROITS ET/OU LES AUTRES PARTIES FOURNISSENT LE PROGRAMME EN L’TAT SANS GARANTIE D’AUCUNE SORTE, QU’ELLE SOIT EXPRIME OU IMPLICITE, CECI COMPRENANT, SANS SE LIMITER CELLES-CI, LES GARANTIES IMPLICITES DE COMMERCIALISABILIT ET D’ADQUATION UN OBJECTIF PARTICULIER. VOUS ASSUMEZ LE RISQUE ENTIER CONCERNANT LA QUALIT ET LES PERFORMANCES DU PROGRAMME. DANS L’VENTUALIT O LE PROGRAMME S’AVRERAIT DFECTUEUX, VOUS ASSUMEZ LES COTS DE TOUS LESSERVICES, RPARATIONS OU CORRECTIONS NCESSAIRES.

16. Limitation de responsabilit.

EN AUCUNE AUTRE CIRCONSTANCE QUE CELLES REQUISES PAR LA LOI APPLICABLE OU ACCORDES PAR CRIT, UN TITULAIRE DE DROITS SUR LE PROGRAMME, OU TOUT AUTRE PARTIE QUI MODIFIE OU ACHEMINE LE PROGRAMME COMME PERMIS CI-DESSUS, NE PEUT TRE TENU POUR RESPONSABLE ENVERS VOUS POUR LES DOMMAGES, INCLUANT TOUT DOMMAGE GNRAL, SPCIAL, ACCIDENTEL OU INDUIT SURVENANT PAR SUITE DE L’UTILISATION OU DE L’INCAPACIT D’UTILISER LE PROGRAMME (Y COMPRIS, SANS SE LIMITER CELLES-CI, LA PERTE DE DONNES OU L’INEXACTITUDE DES DONNES RETOURNES OU LES PERTES SUBIES PAR VOUS OU DES PARTIES TIERCES OU L’INCAPACIT DU PROGRAMME FONCTIONNER AVEC TOUT AUTRE PROGRAMME), MME SI UN TEL TITULAIRE OU TOUTE AUTRE PARTIEA T AVIS DE LA POSSIBILIT DE TELS DOMMAGES.

17. Interprtation des sections 15 et 16.

Si la dclaration d’absence de garantie et la limitation de responsabilit fournies ci-dessus ne peuvent prendre effet localement selon leurs termes, les cours de justice qui les examinent doivent appliquer la lgislation locale qui approche au plus prs possible une leve absolue de toute responsabilit civile lie au Programme, moins qu’une garantie ou assumation de responsabilit accompagne une copie du Programme en change d’un paiement.

FIN DES TERMES ET CONDITIONS.

Comment appliquer ces termes vos nouveaux programmes

Si vous dveloppez un nouveau programme et voulez qu’il soit le plus possible utilisable par le public, la meilleure faon d’y parvenir et d’en faire un logiciel libre que chacun peut redistribuer et changersuivant ces termes-ci.

Pour appliquer ces termes, attachez les notices suivantes au programme. Il est plus sr de les attacher au dbut de chacun des fichiers sources afin de transporter de faon la plus effective possible l’exclusion de garantie ; et chaque fichier devrait comporter au moins la ligne de rservation de droit (“copyright”) et une indication permettant de savoiro la notice complte peut tre trouve :

    <one line to give the program's name and a brief idea of what it does.>
Copyright (C) <year> <name of author>

This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.

Ajoutez galement les informations permettant de vous contacter par courrier lectronique ou postal.

Si le programme produit une interaction sur un terminal, faites lui afficher une courte notice comme celle-ci lors de son dmarrage en mode interactif :

    <program>  Copyright (C) <year>  <name of author>

This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.

Les commandes hypothtiques “affiche g” and “affiche c” devrait afficher les parties appropries de la Licence Gnrale Publique. Bien sr, les commandes de votre programme peuvent tre diffrentes ; pourune interface graphique, vous pourriez utiliser une bote propos.

Vous devriez galement obtenir de votre employeur (si vous travaillez en tant que programmeur) ou de votre cole un renoncement aux droits de proprit pour ce programme, si ncessaire. Pour plus d’informations ce sujet, et comment appliquer la GPL GNU, consultez<http://www.gnu.org/licenses/>.

La Licence Gnrale Publique GNU ne permet pas d’incorporer votre programme dans des programmes propritaires. Si votre programme est une bibliothque de sous-routines, vous pourriez considrer qu’il serait plus utile de permettre de lier des applications propritaires avec la bibliothque. Si c’est ce que vous voulez faire, utilisez la Licence Gnrale Publique Limite GNU au lieu de cette Licence ; mais d’abord,veuillez lire <http://www.gnu.org/philosophy/why-not-lgpl.html>.

================================================ FILE: doc/french/infra_recorder/quick_start.html ================================================ Dmarrage rapide ================================================ FILE: doc/french/infra_recorder/system_requirements.html ================================================ Configuration requise

La configuration requise pour InfraRecorder est la suivante:

  • Windows 98 avec Internet Explorer 5.0 ou plus rcent.
  • 32 Mo de RAM.
  • 8.1 Mo disponible sur le disque dur.
================================================ FILE: doc/french/infra_recorder/whats_new.html ================================================ Quoi de neuf

Version 0.50.0.0

  • Relaxed default project ISO9660 settings.
  • Made progress dialogs resizable for easier reading.
  • Added wait cursors to time consuming operations.
  • Fixed bug causing failed operations to sometimes be reporeted as successful.
  • Fixed bug causing an error when verifying discs containing single character file or directory names.
  • Updated cdrtools to version 2.01.01a61.
  • Added support for displaying BluRay and HD-DVD capabilities.
  • Displayed OK button problem should now be gone.
  • Greatly improved device detection speed, devices are now always probed at startup.
  • Fixed a bug preventing boot images from being removed from projects.
  • Updated InfraRecorder projects not to store file size information that potentially could cause write errors.
  • Added safety net preventing non-recoverable read errors to affect integrity of other files during recording operation.
  • Updated InfraRecorder to lock files on hard drive during file system creation in order to avoid inconsistency errors.
  • Added support for importing data from file lists like M3U.
  • Added command line options for selecting default project and media type.
  • Fixed a bug causing projects opened by association not to be loaded if welcome screen was enabled.
  • Added support for using Ctrl+A in the track secion to select all tracks.
  • The drive letter is now displayed with the name of all CD/DVD devices.
  • Renamed disc fixation to disc closing.
  • Fixed bugs related to drive letter detection.

Version 0.46.2.0

  • Fixed a bug causing the disc file system creation process to hang on some systems (for real this time).
  • Fixed a bug causing a custom temporary directory not to be used.
  • Fixed a start-up maximization bug.

Version 0.46.1.0

  • Fixed a bug causing the disc file system creation process to hang on some systems.

Version 0.46.0.0

  • Minor bugfixes and updates.
  • Added support for recording multiple copies.
  • Added a welcome screen to the InfraRecorder main application and removed the express application.
  • Solved a bug causing the OK button not to be enabled after erasing or formatting a disc.
  • Moved all source code to GPL version 3.
  • Removed cdrtools binaries in favor of cdrkit binaries.
  • Improved device detection routines, there should not be any more problems with wrongly detected drive letters.
  • Included an Indonesian translation, thanks to Andhika Padmawan!
  • Included a Chuvash translation, thanks to Vladimir Kozhevnikov!
  • Fixed a bug causing the express application and shell extension not to be translated.
  • Updated the portable version of InfraRecorder to store its log files in the program directory instead of in the the application data folder.

Version 0.45.0.0

  • Updated cdrtools to version 2.01.01a38.
  • Fixed a bug making InfraRecorder crash when trying to move a folder to itself.
  • Fixed a bug causing the wrong folder to be opened when double-clicking in the project list view when a project contained folders with identical names.
  • Fixed a bug causing the focus not to be returned to the OK button in the progress dialog after performing an operation.
  • Fixed icon rendering error on Windows XP and newer where display depth is lower than 32-bits.
  • Changed the option to verify the device configuration at start up to be enabled by default.
  • Added support for associating InfraRecorder with disc images.
  • Updated the some of the dialog windows to be minimizable and visible on the task bar when launced by an external application (like irExpress).
  • Fixed a bug causing incorrect file names to be used when verifying recorded discs.
  • Added functionallity to rename and remove files from imported sessions.
  • Added support for selecting which multi-session track to import.
  • When trying to record to a non-empty rewritable disc, InfraRecorder now asks if the disc should be erased.
  • When performing an operation the progress is now also displayed in the taskbar.
  • Reduced memory usage when dealing with projects.
  • Fixed a bug making it impossible to open saved projects containing no files.
  • Included a Thai translation, thanks to Prasit Kaephukhieo!
  • Improved compatibility with the ISO9660 standard.
  • Added support for creating UDF-only file systems.
  • Added support for Unicode files names in Joliet extension and UDF file system.
  • Added support for fragmented files in ISO9660 level 3. Files larger than 4 GiB can now be recorded to an ISO9660 file system.
  • Removed mkisofs and isoinfo dependencies.
  • Fixed some bugs related to importing disc sessions.
  • Added properties menu item when right-clicking on the project tree root node.
  • Added proper flagging of hidden files in the disc file system.
  • Changed the default write method for multi-session projects to TAO.
  • Fixed a bug causing InfraRecorder to crash when renaming project files to include slash or backslash characters.
  • Added the .img extension to the list of supported disc image extensions.
  • A few cosmetic changes.
  • Included an Arabic translation, thanks to Circoficus!
  • Included a Greek translation, thanks to . !

Version 0.44.1.0

  • Introduced alternate ways of fetching recorder write speeds. This solves the "disabled OK button problem".
  • Added support for reloading laptop drives (drives that can not automatically load themselves) before starting the disc verification process.
  • Corrected a version display error in the log system.

Version 0.44.0.0

  • Added a warning message when disabling disc fixation since some users believes that this will create a multi-session disc.
  • It's now possible to perform a disc copy using the same device as source and target.
  • Updated drive speed detection routines, it should now detect correct speeds depeding on the inserted media.
  • Improved the media removal/insertion auto detection routines.
  • Added support for switching through the controls of the main view using the tab key.
  • Fixed a bug causing InfraRecorder to crash on Windows 9x systems when changing folder in the explorer view.
  • Added menu items for selecting all files and inverting the file selection.
  • Fixed a bug causing negative progress to be displayed in some cases.
  • Updated InfraRecorder to correctly maximize on startup, if closed maximized.
  • Added a website button to the about window.
  • Fixed a project file rename bug.
  • Made the toolbar customizable in several ways.
  • Improved project file handling, no duplicate files or folders are allowed.
  • The program configuration is now stored in the application data folder. A new portable version of InfraRecorder has been created where data is stored in the program folder.
  • Greatly improved drag and drop functionality.
  • Included a Norwegian translation, thanks to Karol Ptasinski!
  • Updated the help file with index and search capabilities.
  • Fixed a bug causing InfraRecorder to try to verify files that where imported from previous sessions.
  • Fixed a bug causing the disc to be ejected (if requested) before starting the disc verification process.
  • Fixed a bug causing incompatibility with Windows 9x systems due to a function call to SHGetFolderPathA.

Version 0.43.1.0

  • Updated the cdrtools to version 2.01.01a26.
  • Included a Finnish translation, thanks to Rami Aalto!
  • Removed the error message related to ckEffects.exe.
  • Improved the erase feature with support for more recorders.
  • Fixed a bug causing the size and position of the main window not to be remembered.
  • Fixed a bug causing the explorer view to turn white when double-clicking on a folder in the explorer list view (Windows XP only).
  • Improved the program log functionality.
  • Fixed a bug making it impossible to import sessions from certain disc types.
  • Improved the explorer view performance. Expanding anything under "My Computer" in the tree could on some systems result in a long delay because of slow queries to floppy drives.

Version 0.43.0.0

  • Fixed a bug raising an exception when re-ordering audio tracks.
  • Added a smoke effect when writing to a disc (requires Windows Vista Aero to be enabled).
  • Fixed a few bugs causing wrong disc information to be shown in the disc information window.
  • Various adaptations for Windows Vista.
  • Added support for dropping files into the project tree view.
  • Completely rewritten disc erase/format code. Improved DVDRW and DVD-RAM support.
  • Included a Catalan translation, thanks to Josep Llus Amador Teruel!
  • Included a Galician translation, thanks to Xess Estvez!
  • Fixed a bug causing InfraRecorder to have invalid window coordinates closed while minimized.
  • Included a Romanian translation, thanks to Nicolae Crefelean!
  • Removed the Visual C++ 8 DLL dependencies from the shell extension.
  • Included a Hungarian translation, thanks to Tibor Srkny!
  • Included a Hebrew translation, thanks to Shemesh!
  • Included a Danish translation, thanks to Patrick Fust!
  • Fixed a bug causing all internal SCSI commands not to be executed in the x64 build of InfraRecorder.

Version 0.42.1.0

  • The MSI installer used for the x64 release now creates the start-menu shortcuts in a subfolder.
  • Fixed a bug causing InfraRecorder to crash when cdrecord reported recording on a track-number higher than the number of tracks to be recorded.
  • Removed the Visual C++ 8 DLL dependencies from the irWave codec.
  • Fixed a bug causing stack corruption when using the irWMA codec.

Version 0.42.0.0

  • Available as 64-bit (x64) build.
  • Created a completely new Wave codec to remove the libsndfile dependency and add support for the x64 compiler.
  • Modifed the translation system to allow translated controls to automatically resize and move its neightbours when needed.
  • Various changes for Windows Vista compatibility.
  • Modified the WMA codec so it doesn't raise an error message when it fails to load (if Windows Media Player not installed).
  • Included a Japanese translation, thanks to Nardog!
  • Fixed a bug causing DVD media to always be recorded at maximum speed.
  • Included a Korean translation, thanks to Jung Jin-ho!
  • Included a Bulgarian translation, thanks to Iliyan Popov!
  • Separated data DVD from data CD projects.
  • Added support for omiting version numbers from ISO9660 file names.
  • Added support for using Rock Ridge extensions without using the Joliet file name extension.
  • Fixed a bug causing the write speed not to be properly reported on some recorders.
  • Added support for column sorting.
  • Added support for rearranging audio tracks by drag and drop.
  • Included a Serbian (Cyrillic and Latin) translation, thanks to ozzii!
  • Added support for automatically verifying a disc after it has been recorded.
  • Made the labels on the progress dialog double buffered to avoid flickering.
  • Fixed a bug causing the cp1250 code page not to be properly detected on Czech systems.
  • Added support for creating DVD-Video projects.
  • Included a Slovak translation, thanks to Marek!
  • Fixed a bug causing problems when importing certain seasons from multi-session discs.
  • Fixed a bug causing project UDF-settings not to be properly reset when creating a new project.
  • Fixed a bug causing error messages not to be properly displayed when recording custom projects on the fly.
  • Included a Chinese (Traditional) translation, thanks to Charlie!

Version 0.41.0.0

  • Fixed a bug causing the space meter to display inaccurate file sizes on audio files in mixed-mode projects.
  • Due to limitations in the Microsoft Windows 9x Unicode Layer, a non-unicode version of InfraRecorder is released separateley.
  • Added support for disabling the error message that occurs when a codec fails to load.
  • Added support for generating DVD-Video compliant filesystems.
  • Added support for UDF.
  • Added support for creating bootable data discs.
  • Fixed a major bug preventing some projects from beeing properly loaded.
  • Included a Bosnian translation, thanks to Asim Husanovic!
  • Added an option to change the detected write speed of a recorder.
  • Changed the recorder speed management to now allow a larger number of write speeds below the maximum speed.
  • Added write method information to the advanced device details.
  • Fixed a bug causing a wrong character set to be detected on systems using code page 1251.
  • Fixed a bug causing bogus unix file permissions to be set when recording custom projects using the Joliet name extension.
  • Improved the project space meter.
  • Added support for recording custom projects on the fly.
  • Fixed a bug causing a temporary file not to be removed when copying a disc.
  • Added support for disabling the unsupported character set error message.
  • Fixed a bug causing the space meter tooltip to display the size information in bytes instead of minutes when dealing with audio projects.
  • Included a Slovenian translation, thanks to Frani Žižek!
  • Included a Ukrainian translation and manual, thanks to Serhij Dubyk!
  • The advanced device properties list now correctly displays titletip when a feature description is to long to be fully displayed.
  • Fixed a bug causing empty directories to be ignored when creating and recording custom projects.
  • Fixed a bug causing files that has equal characters in the file name to raise an error when creating a disc image.
  • Included a Portuguese (Brazilian) translation, thanks to der Silva!
  • Included a Chinese (Simplified) translation, thanks to DouDeHou!
  • Added more read options (ignore read errors, read sub-channel data and TOC, read speed).
  • Added support for disc cloning.
  • Added support for changing the FIFO buffer size.
  • Added support for ISO level 4 which among many thigs allows directory nesting to be deeper than eight levels.

Version 0.40.0.0

  • Included a Czech translation, thanks to khagaroth!
  • Improved DVD-support (official cdrtools has DVD support since version 2.01.01a09).
  • Simulation mode now works when recording to DVDs.
  • Support for blanking DVD+RW media (currently only with Ricoh based drives).
  • The size and position of the main InfraRecorder window is now remembered and restored each startup.
  • Included a Basque translation, thanks to David Garca-Abad!
  • Added support for encoding audio tracks to Ogg, WMA and MP3 (separate package due to patent issue).
  • Fixed a bug causing the wrong tracks to be displayed when scanning a disc for errors.
  • Added support for decoding MP3, Ogg and WMA audio.
  • Included a German manual, thanks to CE4!
  • Included an Italian translation, thanks to Lorenzo Festa!
  • Fixed bug with message boxes, they should now be modal.
  • Added support for translated manuals.
  • Changed the default simulation value to off.
  • Added an option for changing the temporary folder.
  • Added help documentation on how to make the InfraRecorder installer perform unattended installations.
  • The installer now adds an entry to Add/Remove Programs.
  • Added support for selecting installation language on unattended installations.
  • Included a Russian translation and manual, thanks to Roman Starikh!
  • Included a German translation, thanks to Thomas Bigler!
  • Included a Polish translation, thanks to DJD!
  • Included a Turkish translation, thanks to Fatma Akarslan!
  • Included a Croatian translation, thanks to Tibor Keser!
  • Included a Dutch translation, thanks to Patrick!

Version 0.31.0.0

  • Included a Portuguese translation, thanks to Cesar Baptista!
  • Included a Spanish translation, thanks to Eduardo Leon!
  • Increased the height of all comboboxes in the GUI to prevent unnecessary scrolling.
  • Fixed some GUI glitches causing black and purple backgrounds on some graphics (only affected systems older than Windows XP).
  • Added a tooltip to the space meter which displays the project size.
  • Added support for pasting files from Windows Explorer into a project.
  • Fixed a bug allowing multiple sessions to imported to a project.

Version 0.30.0.83

  • Fixed a bug (static linking to UpdateLayeredWindow in user32.dll) causing incompatibility with Windows 9x systems.

Version 0.30.0.82 (Beta 2)

  • Added DVD support by patching cdrecord (WARNING: Simulation mode is known not to work when burning DVDs).
  • Included a French translation, thanks to Pierre-Jean Coudert!
  • Changed the default write method to SAO because of DVD compatibility.
  • Updated the installer with extra options and multi-language support.
  • Added a couple of new translateable strings for the progress log output.
  • Made some directory layout changes to the CVS.
================================================ FILE: doc/french/style.css ================================================ /* Generated by KompoZer */ body { margin: 0px; font-weight: normal; font-size: 11px; color: #000000; font-family: Verdana,Arial,Helvetica,sans-serif; height: 100%; background-color: #ffffff; text-align: left; } h1 { font-size: 115%; margin-top: 1em; margin-bottom: 0.6em; } h2 { font-size: 100%; margin-top: 1em; margin-bottom: 0.6em; } ul { list-style-type: disc; margin-left: 1.9em; margin-top: 0.6em; margin-bottom: 0em; } ol { margin-left: 2.9em; margin-top: 0.6em; margin-bottom: 0em; font-weight: bold; } ol span { font-weight: normal; } li { margin-bottom: 0.3em; } p, dl { margin-top: 0.6em; margin-bottom: 0.6em; } hr { margin-top: 0.6em; } dd { padding-top: 0.2em; margin-bottom: 0.6em; margin-left: 0.8em; } #header { border-bottom: 1px solid #9999ff; background: #ccccff none repeat scroll 0% 50%; padding-top: 5px; padding-left: 10px; padding-bottom: 5px; } #location { border-bottom: 1px solid #9999ff; background: #ccccff none repeat scroll 0% 50%; padding-top: 5px; padding-left: 10px; padding-bottom: 5px; } #topic { font-weight: bold; } #content { padding: 10px; overflow: auto; height: 100%; } #footer { background: #ccccff none repeat scroll 0% 50%; text-align: center; position: absolute; bottom: 3pt; width: 100%; } ================================================ FILE: doc/french/stylescript.js ================================================ window.onload = OnSize; window.onresize = OnSize; function OnSize() { var vHeader = document.all.item("header"); var vContent = document.all.item("content"); if (vContent ==null) return; if (vHeader != null) { document.all.content.style.overflow = "auto"; document.all.header.style.width = document.body.offsetWidth; document.all.content.style.width = document.body.offsetWidth - 4; document.all.content.style.top = document.all.header.offsetHeight; if (document.body.offsetHeight > document.all.header.offsetHeight) { document.all.content.style.height = document.body.offsetHeight - document.all.header.offsetHeight - 3; } else { document.all.content.style.height = 0; } } } ================================================ FILE: etc/codecs/readme.txt ================================================ InfraRecorder MP3 Encoder ------------------------- This codec is distributed separateley because of patent issues. Personal and/or commercial use of compiled versions of this codec requires a patent license in some countries. Please check before using this codec. To install this codec, simply copy the appropriate lame.irc file to the InfraRecorder codecs directory. C:\Program Files\InfraRecorder\codecs by default. If you have InfraRecorder running you need to restart it so the codec can be loaded. This package contains two codecs, one for the 32-bit version of InfraRecorder, and one for the 64-bit. To find out which version you should use check the InfraRecorder about window. This software comes with ABSOLUTELY NO WARRANTY. This is free software, and you are welcome to redistribute it under certain conditions; please see the file license.txt in the sourcecode package for more information. ================================================ FILE: etc/translations/install.txt ================================================ To install the translation, place the .irl file (and the .chm file for translations that include a translated manual) in the InfraRecorder\Languages directory. For example: C:\Program Files\InfraRecorder\Languages. ================================================ FILE: etc/translations/readme.txt ================================================ Thank you for your help translating InfraRecorder! The file to be translated is named English.irl. Your translation should use the same file extension and be placed in the "InfraRecorder\Languages" folder. When you send me your translation, please include a translation of the following ten strings (used by the setup program): 01: "InfraRecorder Core Files (required)" 02: "Start Menu Shortcuts" 03: "Desktop Shortcut" 04: "Quick Launch Shortcut" 05: "Language Files" 06: "The core files required to use InfraRecorder." 07: "Adds icons to your start menu for easy access." 08: "Adds an icon to your desktop." 09: "Adds an icon to your quick launch bar." 10: "Language files used for supporting different languages in InfraRecorder." You may include any copyright comments in the beginning of the translation file if you wish. For example: ; InfraRecorder Swedish Translation ; Version 0.44 : Date: November 7th 2007 ; Contact: user@domain.com ; Size: 36 KiB Please note that the section named [translation] not should be translated but contain information about your translation. InfraRecorder 0.40 and newer will support translated help files. If you have translated the help file it should be specified in your translation so that InfraRecorder can find it. To do so, just specify the location and name of the translated help file as value number 0x0004 in the translation section. The translated help file should be placed in the same directory as the translation. Example: [translation] 0x0001=Christian Kindahl 0x0002=November 7th 2007 0x0003=0.44 0x0004=Languages\Swedish.chm The help file value (0x0004) is optional. If your translation does not include a help file this value should not exist. Send your translation to: christian dot kindahl at gmail dot com ================================================ FILE: license.rtf ================================================ {\rtf1\ansi\ansicpg1252\deff0{\fonttbl{\f0\fnil\fcharset0 Courier New;}} {\*\generator Msftedit 5.41.15.1515;}\viewkind4\uc1\pard\lang1033\f0\fs16 GNU GENERAL PUBLIC LICENSE\par Version 3, 29 June 2007\par \par Copyright (C) 2007 Free Software Foundation, Inc. \par Everyone is permitted to copy and distribute verbatim copies\par of this license document, but changing it is not allowed.\par \par Preamble\par \par The GNU General Public License is a free, copyleft license for\par software and other kinds of works.\par \par The licenses for most software and other practical works are designed\par to take away your freedom to share and change the works. By contrast,\par the GNU General Public License is intended to guarantee your freedom to\par share and change all versions of a program--to make sure it remains free\par software for all its users. We, the Free Software Foundation, use the\par GNU General Public License for most of our software; it applies also to\par any other work released this way by its authors. You can apply it to\par your programs, too.\par \par When we speak of free software, we are referring to freedom, not\par price. Our General Public Licenses are designed to make sure that you\par have the freedom to distribute copies of free software (and charge for\par them if you wish), that you receive source code or can get it if you\par want it, that you can change the software or use pieces of it in new\par free programs, and that you know you can do these things.\par \par To protect your rights, we need to prevent others from denying you\par these rights or asking you to surrender the rights. Therefore, you have\par certain responsibilities if you distribute copies of the software, or if\par you modify it: responsibilities to respect the freedom of others.\par \par For example, if you distribute copies of such a program, whether\par gratis or for a fee, you must pass on to the recipients the same\par freedoms that you received. You must make sure that they, too, receive\par or can get the source code. And you must show them these terms so they\par know their rights.\par \par Developers that use the GNU GPL protect your rights with two steps:\par (1) assert copyright on the software, and (2) offer you this License\par giving you legal permission to copy, distribute and/or modify it.\par \par For the developers' and authors' protection, the GPL clearly explains\par that there is no warranty for this free software. For both users' and\par authors' sake, the GPL requires that modified versions be marked as\par changed, so that their problems will not be attributed erroneously to\par authors of previous versions.\par \par Some devices are designed to deny users access to install or run\par modified versions of the software inside them, although the manufacturer\par can do so. This is fundamentally incompatible with the aim of\par protecting users' freedom to change the software. The systematic\par pattern of such abuse occurs in the area of products for individuals to\par use, which is precisely where it is most unacceptable. Therefore, we\par have designed this version of the GPL to prohibit the practice for those\par products. If such problems arise substantially in other domains, we\par stand ready to extend this provision to those domains in future versions\par of the GPL, as needed to protect the freedom of users.\par \par Finally, every program is threatened constantly by software patents.\par States should not allow patents to restrict development and use of\par software on general-purpose computers, but in those that do, we wish to\par avoid the special danger that patents applied to a free program could\par make it effectively proprietary. To prevent this, the GPL assures that\par patents cannot be used to render the program non-free.\par \par The precise terms and conditions for copying, distribution and\par modification follow.\par \par TERMS AND CONDITIONS\par \par 0. Definitions.\par \par "This License" refers to version 3 of the GNU General Public License.\par \par "Copyright" also means copyright-like laws that apply to other kinds of\par works, such as semiconductor masks.\par \par "The Program" refers to any copyrightable work licensed under this\par License. Each licensee is addressed as "you". "Licensees" and\par "recipients" may be individuals or organizations.\par \par To "modify" a work means to copy from or adapt all or part of the work\par in a fashion requiring copyright permission, other than the making of an\par exact copy. The resulting work is called a "modified version" of the\par earlier work or a work "based on" the earlier work.\par \par A "covered work" means either the unmodified Program or a work based\par on the Program.\par \par To "propagate" a work means to do anything with it that, without\par permission, would make you directly or secondarily liable for\par infringement under applicable copyright law, except executing it on a\par computer or modifying a private copy. Propagation includes copying,\par distribution (with or without modification), making available to the\par public, and in some countries other activities as well.\par \par To "convey" a work means any kind of propagation that enables other\par parties to make or receive copies. Mere interaction with a user through\par a computer network, with no transfer of a copy, is not conveying.\par \par An interactive user interface displays "Appropriate Legal Notices"\par to the extent that it includes a convenient and prominently visible\par feature that (1) displays an appropriate copyright notice, and (2)\par tells the user that there is no warranty for the work (except to the\par extent that warranties are provided), that licensees may convey the\par work under this License, and how to view a copy of this License. If\par the interface presents a list of user commands or options, such as a\par menu, a prominent item in the list meets this criterion.\par \par 1. Source Code.\par \par The "source code" for a work means the preferred form of the work\par for making modifications to it. "Object code" means any non-source\par form of a work.\par \par A "Standard Interface" means an interface that either is an official\par standard defined by a recognized standards body, or, in the case of\par interfaces specified for a particular programming language, one that\par is widely used among developers working in that language.\par \par The "System Libraries" of an executable work include anything, other\par than the work as a whole, that (a) is included in the normal form of\par packaging a Major Component, but which is not part of that Major\par Component, and (b) serves only to enable use of the work with that\par Major Component, or to implement a Standard Interface for which an\par implementation is available to the public in source code form. A\par "Major Component", in this context, means a major essential component\par (kernel, window system, and so on) of the specific operating system\par (if any) on which the executable work runs, or a compiler used to\par produce the work, or an object code interpreter used to run it.\par \par The "Corresponding Source" for a work in object code form means all\par the source code needed to generate, install, and (for an executable\par work) run the object code and to modify the work, including scripts to\par control those activities. However, it does not include the work's\par System Libraries, or general-purpose tools or generally available free\par programs which are used unmodified in performing those activities but\par which are not part of the work. For example, Corresponding Source\par includes interface definition files associated with source files for\par the work, and the source code for shared libraries and dynamically\par linked subprograms that the work is specifically designed to require,\par such as by intimate data communication or control flow between those\par subprograms and other parts of the work.\par \par The Corresponding Source need not include anything that users\par can regenerate automatically from other parts of the Corresponding\par Source.\par \par The Corresponding Source for a work in source code form is that\par same work.\par \par 2. Basic Permissions.\par \par All rights granted under this License are granted for the term of\par copyright on the Program, and are irrevocable provided the stated\par conditions are met. This License explicitly affirms your unlimited\par permission to run the unmodified Program. The output from running a\par covered work is covered by this License only if the output, given its\par content, constitutes a covered work. This License acknowledges your\par rights of fair use or other equivalent, as provided by copyright law.\par \par You may make, run and propagate covered works that you do not\par convey, without conditions so long as your license otherwise remains\par in force. You may convey covered works to others for the sole purpose\par of having them make modifications exclusively for you, or provide you\par with facilities for running those works, provided that you comply with\par the terms of this License in conveying all material for which you do\par not control copyright. Those thus making or running the covered works\par for you must do so exclusively on your behalf, under your direction\par and control, on terms that prohibit them from making any copies of\par your copyrighted material outside their relationship with you.\par \par Conveying under any other circumstances is permitted solely under\par the conditions stated below. Sublicensing is not allowed; section 10\par makes it unnecessary.\par \par 3. Protecting Users' Legal Rights From Anti-Circumvention Law.\par \par No covered work shall be deemed part of an effective technological\par measure under any applicable law fulfilling obligations under article\par 11 of the WIPO copyright treaty adopted on 20 December 1996, or\par similar laws prohibiting or restricting circumvention of such\par measures.\par \par When you convey a covered work, you waive any legal power to forbid\par circumvention of technological measures to the extent such circumvention\par is effected by exercising rights under this License with respect to\par the covered work, and you disclaim any intention to limit operation or\par modification of the work as a means of enforcing, against the work's\par users, your or third parties' legal rights to forbid circumvention of\par technological measures.\par \par 4. Conveying Verbatim Copies.\par \par You may convey verbatim copies of the Program's source code as you\par receive it, in any medium, provided that you conspicuously and\par appropriately publish on each copy an appropriate copyright notice;\par keep intact all notices stating that this License and any\par non-permissive terms added in accord with section 7 apply to the code;\par keep intact all notices of the absence of any warranty; and give all\par recipients a copy of this License along with the Program.\par \par You may charge any price or no price for each copy that you convey,\par and you may offer support or warranty protection for a fee.\par \par 5. Conveying Modified Source Versions.\par \par You may convey a work based on the Program, or the modifications to\par produce it from the Program, in the form of source code under the\par terms of section 4, provided that you also meet all of these conditions:\par \par a) The work must carry prominent notices stating that you modified\par it, and giving a relevant date.\par \par b) The work must carry prominent notices stating that it is\par released under this License and any conditions added under section\par 7. This requirement modifies the requirement in section 4 to\par "keep intact all notices".\par \par c) You must license the entire work, as a whole, under this\par License to anyone who comes into possession of a copy. This\par License will therefore apply, along with any applicable section 7\par additional terms, to the whole of the work, and all its parts,\par regardless of how they are packaged. This License gives no\par permission to license the work in any other way, but it does not\par invalidate such permission if you have separately received it.\par \par d) If the work has interactive user interfaces, each must display\par Appropriate Legal Notices; however, if the Program has interactive\par interfaces that do not display Appropriate Legal Notices, your\par work need not make them do so.\par \par A compilation of a covered work with other separate and independent\par works, which are not by their nature extensions of the covered work,\par and which are not combined with it such as to form a larger program,\par in or on a volume of a storage or distribution medium, is called an\par "aggregate" if the compilation and its resulting copyright are not\par used to limit the access or legal rights of the compilation's users\par beyond what the individual works permit. Inclusion of a covered work\par in an aggregate does not cause this License to apply to the other\par parts of the aggregate.\par \par 6. Conveying Non-Source Forms.\par \par You may convey a covered work in object code form under the terms\par of sections 4 and 5, provided that you also convey the\par machine-readable Corresponding Source under the terms of this License,\par in one of these ways:\par \par a) Convey the object code in, or embodied in, a physical product\par (including a physical distribution medium), accompanied by the\par Corresponding Source fixed on a durable physical medium\par customarily used for software interchange.\par \par b) Convey the object code in, or embodied in, a physical product\par (including a physical distribution medium), accompanied by a\par written offer, valid for at least three years and valid for as\par long as you offer spare parts or customer support for that product\par model, to give anyone who possesses the object code either (1) a\par copy of the Corresponding Source for all the software in the\par product that is covered by this License, on a durable physical\par medium customarily used for software interchange, for a price no\par more than your reasonable cost of physically performing this\par conveying of source, or (2) access to copy the\par Corresponding Source from a network server at no charge.\par \par c) Convey individual copies of the object code with a copy of the\par written offer to provide the Corresponding Source. This\par alternative is allowed only occasionally and noncommercially, and\par only if you received the object code with such an offer, in accord\par with subsection 6b.\par \par d) Convey the object code by offering access from a designated\par place (gratis or for a charge), and offer equivalent access to the\par Corresponding Source in the same way through the same place at no\par further charge. You need not require recipients to copy the\par Corresponding Source along with the object code. If the place to\par copy the object code is a network server, the Corresponding Source\par may be on a different server (operated by you or a third party)\par that supports equivalent copying facilities, provided you maintain\par clear directions next to the object code saying where to find the\par Corresponding Source. Regardless of what server hosts the\par Corresponding Source, you remain obligated to ensure that it is\par available for as long as needed to satisfy these requirements.\par \par e) Convey the object code using peer-to-peer transmission, provided\par you inform other peers where the object code and Corresponding\par Source of the work are being offered to the general public at no\par charge under subsection 6d.\par \par A separable portion of the object code, whose source code is excluded\par from the Corresponding Source as a System Library, need not be\par included in conveying the object code work.\par \par A "User Product" is either (1) a "consumer product", which means any\par tangible personal property which is normally used for personal, family,\par or household purposes, or (2) anything designed or sold for incorporation\par into a dwelling. In determining whether a product is a consumer product,\par doubtful cases shall be resolved in favor of coverage. For a particular\par product received by a particular user, "normally used" refers to a\par typical or common use of that class of product, regardless of the status\par of the particular user or of the way in which the particular user\par actually uses, or expects or is expected to use, the product. A product\par is a consumer product regardless of whether the product has substantial\par commercial, industrial or non-consumer uses, unless such uses represent\par the only significant mode of use of the product.\par \par "Installation Information" for a User Product means any methods,\par procedures, authorization keys, or other information required to install\par and execute modified versions of a covered work in that User Product from\par a modified version of its Corresponding Source. The information must\par suffice to ensure that the continued functioning of the modified object\par code is in no case prevented or interfered with solely because\par modification has been made.\par \par If you convey an object code work under this section in, or with, or\par specifically for use in, a User Product, and the conveying occurs as\par part of a transaction in which the right of possession and use of the\par User Product is transferred to the recipient in perpetuity or for a\par fixed term (regardless of how the transaction is characterized), the\par Corresponding Source conveyed under this section must be accompanied\par by the Installation Information. But this requirement does not apply\par if neither you nor any third party retains the ability to install\par modified object code on the User Product (for example, the work has\par been installed in ROM).\par \par The requirement to provide Installation Information does not include a\par requirement to continue to provide support service, warranty, or updates\par for a work that has been modified or installed by the recipient, or for\par the User Product in which it has been modified or installed. Access to a\par network may be denied when the modification itself materially and\par adversely affects the operation of the network or violates the rules and\par protocols for communication across the network.\par \par Corresponding Source conveyed, and Installation Information provided,\par in accord with this section must be in a format that is publicly\par documented (and with an implementation available to the public in\par source code form), and must require no special password or key for\par unpacking, reading or copying.\par \par 7. Additional Terms.\par \par "Additional permissions" are terms that supplement the terms of this\par License by making exceptions from one or more of its conditions.\par Additional permissions that are applicable to the entire Program shall\par be treated as though they were included in this License, to the extent\par that they are valid under applicable law. If additional permissions\par apply only to part of the Program, that part may be used separately\par under those permissions, but the entire Program remains governed by\par this License without regard to the additional permissions.\par \par When you convey a copy of a covered work, you may at your option\par remove any additional permissions from that copy, or from any part of\par it. (Additional permissions may be written to require their own\par removal in certain cases when you modify the work.) You may place\par additional permissions on material, added by you to a covered work,\par for which you have or can give appropriate copyright permission.\par \par Notwithstanding any other provision of this License, for material you\par add to a covered work, you may (if authorized by the copyright holders of\par that material) supplement the terms of this License with terms:\par \par a) Disclaiming warranty or limiting liability differently from the\par terms of sections 15 and 16 of this License; or\par \par b) Requiring preservation of specified reasonable legal notices or\par author attributions in that material or in the Appropriate Legal\par Notices displayed by works containing it; or\par \par c) Prohibiting misrepresentation of the origin of that material, or\par requiring that modified versions of such material be marked in\par reasonable ways as different from the original version; or\par \par d) Limiting the use for publicity purposes of names of licensors or\par authors of the material; or\par \par e) Declining to grant rights under trademark law for use of some\par trade names, trademarks, or service marks; or\par \par f) Requiring indemnification of licensors and authors of that\par material by anyone who conveys the material (or modified versions of\par it) with contractual assumptions of liability to the recipient, for\par any liability that these contractual assumptions directly impose on\par those licensors and authors.\par \par All other non-permissive additional terms are considered "further\par restrictions" within the meaning of section 10. If the Program as you\par received it, or any part of it, contains a notice stating that it is\par governed by this License along with a term that is a further\par restriction, you may remove that term. If a license document contains\par a further restriction but permits relicensing or conveying under this\par License, you may add to a covered work material governed by the terms\par of that license document, provided that the further restriction does\par not survive such relicensing or conveying.\par \par If you add terms to a covered work in accord with this section, you\par must place, in the relevant source files, a statement of the\par additional terms that apply to those files, or a notice indicating\par where to find the applicable terms.\par \par Additional terms, permissive or non-permissive, may be stated in the\par form of a separately written license, or stated as exceptions;\par the above requirements apply either way.\par \par 8. Termination.\par \par You may not propagate or modify a covered work except as expressly\par provided under this License. Any attempt otherwise to propagate or\par modify it is void, and will automatically terminate your rights under\par this License (including any patent licenses granted under the third\par paragraph of section 11).\par \par However, if you cease all violation of this License, then your\par license from a particular copyright holder is reinstated (a)\par provisionally, unless and until the copyright holder explicitly and\par finally terminates your license, and (b) permanently, if the copyright\par holder fails to notify you of the violation by some reasonable means\par prior to 60 days after the cessation.\par \par Moreover, your license from a particular copyright holder is\par reinstated permanently if the copyright holder notifies you of the\par violation by some reasonable means, this is the first time you have\par received notice of violation of this License (for any work) from that\par copyright holder, and you cure the violation prior to 30 days after\par your receipt of the notice.\par \par Termination of your rights under this section does not terminate the\par licenses of parties who have received copies or rights from you under\par this License. If your rights have been terminated and not permanently\par reinstated, you do not qualify to receive new licenses for the same\par material under section 10.\par \par 9. Acceptance Not Required for Having Copies.\par \par You are not required to accept this License in order to receive or\par run a copy of the Program. Ancillary propagation of a covered work\par occurring solely as a consequence of using peer-to-peer transmission\par to receive a copy likewise does not require acceptance. However,\par nothing other than this License grants you permission to propagate or\par modify any covered work. These actions infringe copyright if you do\par not accept this License. Therefore, by modifying or propagating a\par covered work, you indicate your acceptance of this License to do so.\par \par 10. Automatic Licensing of Downstream Recipients.\par \par Each time you convey a covered work, the recipient automatically\par receives a license from the original licensors, to run, modify and\par propagate that work, subject to this License. You are not responsible\par for enforcing compliance by third parties with this License.\par \par An "entity transaction" is a transaction transferring control of an\par organization, or substantially all assets of one, or subdividing an\par organization, or merging organizations. If propagation of a covered\par work results from an entity transaction, each party to that\par transaction who receives a copy of the work also receives whatever\par licenses to the work the party's predecessor in interest had or could\par give under the previous paragraph, plus a right to possession of the\par Corresponding Source of the work from the predecessor in interest, if\par the predecessor has it or can get it with reasonable efforts.\par \par You may not impose any further restrictions on the exercise of the\par rights granted or affirmed under this License. For example, you may\par not impose a license fee, royalty, or other charge for exercise of\par rights granted under this License, and you may not initiate litigation\par (including a cross-claim or counterclaim in a lawsuit) alleging that\par any patent claim is infringed by making, using, selling, offering for\par sale, or importing the Program or any portion of it.\par \par 11. Patents.\par \par A "contributor" is a copyright holder who authorizes use under this\par License of the Program or a work on which the Program is based. The\par work thus licensed is called the contributor's "contributor version".\par \par A contributor's "essential patent claims" are all patent claims\par owned or controlled by the contributor, whether already acquired or\par hereafter acquired, that would be infringed by some manner, permitted\par by this License, of making, using, or selling its contributor version,\par but do not include claims that would be infringed only as a\par consequence of further modification of the contributor version. For\par purposes of this definition, "control" includes the right to grant\par patent sublicenses in a manner consistent with the requirements of\par this License.\par \par Each contributor grants you a non-exclusive, worldwide, royalty-free\par patent license under the contributor's essential patent claims, to\par make, use, sell, offer for sale, import and otherwise run, modify and\par propagate the contents of its contributor version.\par \par In the following three paragraphs, a "patent license" is any express\par agreement or commitment, however denominated, not to enforce a patent\par (such as an express permission to practice a patent or covenant not to\par sue for patent infringement). To "grant" such a patent license to a\par party means to make such an agreement or commitment not to enforce a\par patent against the party.\par \par If you convey a covered work, knowingly relying on a patent license,\par and the Corresponding Source of the work is not available for anyone\par to copy, free of charge and under the terms of this License, through a\par publicly available network server or other readily accessible means,\par then you must either (1) cause the Corresponding Source to be so\par available, or (2) arrange to deprive yourself of the benefit of the\par patent license for this particular work, or (3) arrange, in a manner\par consistent with the requirements of this License, to extend the patent\par license to downstream recipients. "Knowingly relying" means you have\par actual knowledge that, but for the patent license, your conveying the\par covered work in a country, or your recipient's use of the covered work\par in a country, would infringe one or more identifiable patents in that\par country that you have reason to believe are valid.\par \par If, pursuant to or in connection with a single transaction or\par arrangement, you convey, or propagate by procuring conveyance of, a\par covered work, and grant a patent license to some of the parties\par receiving the covered work authorizing them to use, propagate, modify\par or convey a specific copy of the covered work, then the patent license\par you grant is automatically extended to all recipients of the covered\par work and works based on it.\par \par A patent license is "discriminatory" if it does not include within\par the scope of its coverage, prohibits the exercise of, or is\par conditioned on the non-exercise of one or more of the rights that are\par specifically granted under this License. You may not convey a covered\par work if you are a party to an arrangement with a third party that is\par in the business of distributing software, under which you make payment\par to the third party based on the extent of your activity of conveying\par the work, and under which the third party grants, to any of the\par parties who would receive the covered work from you, a discriminatory\par patent license (a) in connection with copies of the covered work\par conveyed by you (or copies made from those copies), or (b) primarily\par for and in connection with specific products or compilations that\par contain the covered work, unless you entered into that arrangement,\par or that patent license was granted, prior to 28 March 2007.\par \par Nothing in this License shall be construed as excluding or limiting\par any implied license or other defenses to infringement that may\par otherwise be available to you under applicable patent law.\par \par 12. No Surrender of Others' Freedom.\par \par If conditions are imposed on you (whether by court order, agreement or\par otherwise) that contradict the conditions of this License, they do not\par excuse you from the conditions of this License. If you cannot convey a\par covered work so as to satisfy simultaneously your obligations under this\par License and any other pertinent obligations, then as a consequence you may\par not convey it at all. For example, if you agree to terms that obligate you\par to collect a royalty for further conveying from those to whom you convey\par the Program, the only way you could satisfy both those terms and this\par License would be to refrain entirely from conveying the Program.\par \par 13. Use with the GNU Affero General Public License.\par \par Notwithstanding any other provision of this License, you have\par permission to link or combine any covered work with a work licensed\par under version 3 of the GNU Affero General Public License into a single\par combined work, and to convey the resulting work. The terms of this\par License will continue to apply to the part which is the covered work,\par but the special requirements of the GNU Affero General Public License,\par section 13, concerning interaction through a network will apply to the\par combination as such.\par \par 14. Revised Versions of this License.\par \par The Free Software Foundation may publish revised and/or new versions of\par the GNU General Public License from time to time. Such new versions will\par be similar in spirit to the present version, but may differ in detail to\par address new problems or concerns.\par \par Each version is given a distinguishing version number. If the\par Program specifies that a certain numbered version of the GNU General\par Public License "or any later version" applies to it, you have the\par option of following the terms and conditions either of that numbered\par version or of any later version published by the Free Software\par Foundation. If the Program does not specify a version number of the\par GNU General Public License, you may choose any version ever published\par by the Free Software Foundation.\par \par If the Program specifies that a proxy can decide which future\par versions of the GNU General Public License can be used, that proxy's\par public statement of acceptance of a version permanently authorizes you\par to choose that version for the Program.\par \par Later license versions may give you additional or different\par permissions. However, no additional obligations are imposed on any\par author or copyright holder as a result of your choosing to follow a\par later version.\par \par 15. Disclaimer of Warranty.\par \par THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY\par APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT\par HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY\par OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO,\par THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR\par PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM\par IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF\par ALL NECESSARY SERVICING, REPAIR OR CORRECTION.\par \par 16. Limitation of Liability.\par \par IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING\par WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS\par THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY\par GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE\par USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF\par DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD\par PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS),\par EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF\par SUCH DAMAGES.\par \par 17. Interpretation of Sections 15 and 16.\par \par If the disclaimer of warranty and limitation of liability provided\par above cannot be given local legal effect according to their terms,\par reviewing courts shall apply local law that most closely approximates\par an absolute waiver of all civil liability in connection with the\par Program, unless a warranty or assumption of liability accompanies a\par copy of the Program in return for a fee.\par \par END OF TERMS AND CONDITIONS\par \par How to Apply These Terms to Your New Programs\par \par If you develop a new program, and you want it to be of the greatest\par possible use to the public, the best way to achieve this is to make it\par free software which everyone can redistribute and change under these terms.\par \par To do so, attach the following notices to the program. It is safest\par to attach them to the start of each source file to most effectively\par state the exclusion of warranty; and each file should have at least\par the "copyright" line and a pointer to where the full notice is found.\par \par \par Copyright (C) \par \par This program is free software: you can redistribute it and/or modify\par it under the terms of the GNU General Public License as published by\par the Free Software Foundation, either version 3 of the License, or\par (at your option) any later version.\par \par This program is distributed in the hope that it will be useful,\par but WITHOUT ANY WARRANTY; without even the implied warranty of\par MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\par GNU General Public License for more details.\par \par You should have received a copy of the GNU General Public License\par along with this program. If not, see .\par \par Also add information on how to contact you by electronic and paper mail.\par \par If the program does terminal interaction, make it output a short\par notice like this when it starts in an interactive mode:\par \par Copyright (C) \par This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.\par This is free software, and you are welcome to redistribute it\par under certain conditions; type `show c' for details.\par \par The hypothetical commands `show w' and `show c' should show the appropriate\par parts of the General Public License. Of course, your program's commands\par might be different; for a GUI interface, you would use an "about box".\par \par You should also get your employer (if you work as a programmer) or school,\par if any, to sign a "copyright disclaimer" for the program, if necessary.\par For more information on this, and how to apply and follow the GNU GPL, see\par .\par \par The GNU General Public License does not permit incorporating your program\par into proprietary programs. If your program is a subroutine library, you\par may consider it more useful to permit linking proprietary applications with\par the library. If this is what you want to do, use the GNU Lesser General\par Public License instead of this License. But first, please read\par .\par \par } ================================================ FILE: license.txt ================================================ GNU GENERAL PUBLIC LICENSE Version 3, 29 June 2007 Copyright (C) 2007 Free Software Foundation, Inc. Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. Preamble The GNU General Public License is a free, copyleft license for software and other kinds of works. The licenses for most software and other practical works are designed to take away your freedom to share and change the works. By contrast, the GNU General Public License is intended to guarantee your freedom to share and change all versions of a program--to make sure it remains free software for all its users. We, the Free Software Foundation, use the GNU General Public License for most of our software; it applies also to any other work released this way by its authors. You can apply it to your programs, too. When we speak of free software, we are referring to freedom, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for them if you wish), that you receive source code or can get it if you want it, that you can change the software or use pieces of it in new free programs, and that you know you can do these things. To protect your rights, we need to prevent others from denying you these rights or asking you to surrender the rights. Therefore, you have certain responsibilities if you distribute copies of the software, or if you modify it: responsibilities to respect the freedom of others. For example, if you distribute copies of such a program, whether gratis or for a fee, you must pass on to the recipients the same freedoms that you received. You must make sure that they, too, receive or can get the source code. And you must show them these terms so they know their rights. Developers that use the GNU GPL protect your rights with two steps: (1) assert copyright on the software, and (2) offer you this License giving you legal permission to copy, distribute and/or modify it. For the developers' and authors' protection, the GPL clearly explains that there is no warranty for this free software. For both users' and authors' sake, the GPL requires that modified versions be marked as changed, so that their problems will not be attributed erroneously to authors of previous versions. Some devices are designed to deny users access to install or run modified versions of the software inside them, although the manufacturer can do so. This is fundamentally incompatible with the aim of protecting users' freedom to change the software. The systematic pattern of such abuse occurs in the area of products for individuals to use, which is precisely where it is most unacceptable. Therefore, we have designed this version of the GPL to prohibit the practice for those products. If such problems arise substantially in other domains, we stand ready to extend this provision to those domains in future versions of the GPL, as needed to protect the freedom of users. Finally, every program is threatened constantly by software patents. States should not allow patents to restrict development and use of software on general-purpose computers, but in those that do, we wish to avoid the special danger that patents applied to a free program could make it effectively proprietary. To prevent this, the GPL assures that patents cannot be used to render the program non-free. The precise terms and conditions for copying, distribution and modification follow. TERMS AND CONDITIONS 0. Definitions. "This License" refers to version 3 of the GNU General Public License. "Copyright" also means copyright-like laws that apply to other kinds of works, such as semiconductor masks. "The Program" refers to any copyrightable work licensed under this License. Each licensee is addressed as "you". "Licensees" and "recipients" may be individuals or organizations. To "modify" a work means to copy from or adapt all or part of the work in a fashion requiring copyright permission, other than the making of an exact copy. The resulting work is called a "modified version" of the earlier work or a work "based on" the earlier work. A "covered work" means either the unmodified Program or a work based on the Program. To "propagate" a work means to do anything with it that, without permission, would make you directly or secondarily liable for infringement under applicable copyright law, except executing it on a computer or modifying a private copy. Propagation includes copying, distribution (with or without modification), making available to the public, and in some countries other activities as well. To "convey" a work means any kind of propagation that enables other parties to make or receive copies. Mere interaction with a user through a computer network, with no transfer of a copy, is not conveying. An interactive user interface displays "Appropriate Legal Notices" to the extent that it includes a convenient and prominently visible feature that (1) displays an appropriate copyright notice, and (2) tells the user that there is no warranty for the work (except to the extent that warranties are provided), that licensees may convey the work under this License, and how to view a copy of this License. If the interface presents a list of user commands or options, such as a menu, a prominent item in the list meets this criterion. 1. Source Code. The "source code" for a work means the preferred form of the work for making modifications to it. "Object code" means any non-source form of a work. A "Standard Interface" means an interface that either is an official standard defined by a recognized standards body, or, in the case of interfaces specified for a particular programming language, one that is widely used among developers working in that language. The "System Libraries" of an executable work include anything, other than the work as a whole, that (a) is included in the normal form of packaging a Major Component, but which is not part of that Major Component, and (b) serves only to enable use of the work with that Major Component, or to implement a Standard Interface for which an implementation is available to the public in source code form. A "Major Component", in this context, means a major essential component (kernel, window system, and so on) of the specific operating system (if any) on which the executable work runs, or a compiler used to produce the work, or an object code interpreter used to run it. The "Corresponding Source" for a work in object code form means all the source code needed to generate, install, and (for an executable work) run the object code and to modify the work, including scripts to control those activities. However, it does not include the work's System Libraries, or general-purpose tools or generally available free programs which are used unmodified in performing those activities but which are not part of the work. For example, Corresponding Source includes interface definition files associated with source files for the work, and the source code for shared libraries and dynamically linked subprograms that the work is specifically designed to require, such as by intimate data communication or control flow between those subprograms and other parts of the work. The Corresponding Source need not include anything that users can regenerate automatically from other parts of the Corresponding Source. The Corresponding Source for a work in source code form is that same work. 2. Basic Permissions. All rights granted under this License are granted for the term of copyright on the Program, and are irrevocable provided the stated conditions are met. This License explicitly affirms your unlimited permission to run the unmodified Program. The output from running a covered work is covered by this License only if the output, given its content, constitutes a covered work. This License acknowledges your rights of fair use or other equivalent, as provided by copyright law. You may make, run and propagate covered works that you do not convey, without conditions so long as your license otherwise remains in force. You may convey covered works to others for the sole purpose of having them make modifications exclusively for you, or provide you with facilities for running those works, provided that you comply with the terms of this License in conveying all material for which you do not control copyright. Those thus making or running the covered works for you must do so exclusively on your behalf, under your direction and control, on terms that prohibit them from making any copies of your copyrighted material outside their relationship with you. Conveying under any other circumstances is permitted solely under the conditions stated below. Sublicensing is not allowed; section 10 makes it unnecessary. 3. Protecting Users' Legal Rights From Anti-Circumvention Law. No covered work shall be deemed part of an effective technological measure under any applicable law fulfilling obligations under article 11 of the WIPO copyright treaty adopted on 20 December 1996, or similar laws prohibiting or restricting circumvention of such measures. When you convey a covered work, you waive any legal power to forbid circumvention of technological measures to the extent such circumvention is effected by exercising rights under this License with respect to the covered work, and you disclaim any intention to limit operation or modification of the work as a means of enforcing, against the work's users, your or third parties' legal rights to forbid circumvention of technological measures. 4. Conveying Verbatim Copies. You may convey verbatim copies of the Program's source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice; keep intact all notices stating that this License and any non-permissive terms added in accord with section 7 apply to the code; keep intact all notices of the absence of any warranty; and give all recipients a copy of this License along with the Program. You may charge any price or no price for each copy that you convey, and you may offer support or warranty protection for a fee. 5. Conveying Modified Source Versions. You may convey a work based on the Program, or the modifications to produce it from the Program, in the form of source code under the terms of section 4, provided that you also meet all of these conditions: a) The work must carry prominent notices stating that you modified it, and giving a relevant date. b) The work must carry prominent notices stating that it is released under this License and any conditions added under section 7. This requirement modifies the requirement in section 4 to "keep intact all notices". c) You must license the entire work, as a whole, under this License to anyone who comes into possession of a copy. This License will therefore apply, along with any applicable section 7 additional terms, to the whole of the work, and all its parts, regardless of how they are packaged. This License gives no permission to license the work in any other way, but it does not invalidate such permission if you have separately received it. d) If the work has interactive user interfaces, each must display Appropriate Legal Notices; however, if the Program has interactive interfaces that do not display Appropriate Legal Notices, your work need not make them do so. A compilation of a covered work with other separate and independent works, which are not by their nature extensions of the covered work, and which are not combined with it such as to form a larger program, in or on a volume of a storage or distribution medium, is called an "aggregate" if the compilation and its resulting copyright are not used to limit the access or legal rights of the compilation's users beyond what the individual works permit. Inclusion of a covered work in an aggregate does not cause this License to apply to the other parts of the aggregate. 6. Conveying Non-Source Forms. You may convey a covered work in object code form under the terms of sections 4 and 5, provided that you also convey the machine-readable Corresponding Source under the terms of this License, in one of these ways: a) Convey the object code in, or embodied in, a physical product (including a physical distribution medium), accompanied by the Corresponding Source fixed on a durable physical medium customarily used for software interchange. b) Convey the object code in, or embodied in, a physical product (including a physical distribution medium), accompanied by a written offer, valid for at least three years and valid for as long as you offer spare parts or customer support for that product model, to give anyone who possesses the object code either (1) a copy of the Corresponding Source for all the software in the product that is covered by this License, on a durable physical medium customarily used for software interchange, for a price no more than your reasonable cost of physically performing this conveying of source, or (2) access to copy the Corresponding Source from a network server at no charge. c) Convey individual copies of the object code with a copy of the written offer to provide the Corresponding Source. This alternative is allowed only occasionally and noncommercially, and only if you received the object code with such an offer, in accord with subsection 6b. d) Convey the object code by offering access from a designated place (gratis or for a charge), and offer equivalent access to the Corresponding Source in the same way through the same place at no further charge. You need not require recipients to copy the Corresponding Source along with the object code. If the place to copy the object code is a network server, the Corresponding Source may be on a different server (operated by you or a third party) that supports equivalent copying facilities, provided you maintain clear directions next to the object code saying where to find the Corresponding Source. Regardless of what server hosts the Corresponding Source, you remain obligated to ensure that it is available for as long as needed to satisfy these requirements. e) Convey the object code using peer-to-peer transmission, provided you inform other peers where the object code and Corresponding Source of the work are being offered to the general public at no charge under subsection 6d. A separable portion of the object code, whose source code is excluded from the Corresponding Source as a System Library, need not be included in conveying the object code work. A "User Product" is either (1) a "consumer product", which means any tangible personal property which is normally used for personal, family, or household purposes, or (2) anything designed or sold for incorporation into a dwelling. In determining whether a product is a consumer product, doubtful cases shall be resolved in favor of coverage. For a particular product received by a particular user, "normally used" refers to a typical or common use of that class of product, regardless of the status of the particular user or of the way in which the particular user actually uses, or expects or is expected to use, the product. A product is a consumer product regardless of whether the product has substantial commercial, industrial or non-consumer uses, unless such uses represent the only significant mode of use of the product. "Installation Information" for a User Product means any methods, procedures, authorization keys, or other information required to install and execute modified versions of a covered work in that User Product from a modified version of its Corresponding Source. The information must suffice to ensure that the continued functioning of the modified object code is in no case prevented or interfered with solely because modification has been made. If you convey an object code work under this section in, or with, or specifically for use in, a User Product, and the conveying occurs as part of a transaction in which the right of possession and use of the User Product is transferred to the recipient in perpetuity or for a fixed term (regardless of how the transaction is characterized), the Corresponding Source conveyed under this section must be accompanied by the Installation Information. But this requirement does not apply if neither you nor any third party retains the ability to install modified object code on the User Product (for example, the work has been installed in ROM). The requirement to provide Installation Information does not include a requirement to continue to provide support service, warranty, or updates for a work that has been modified or installed by the recipient, or for the User Product in which it has been modified or installed. Access to a network may be denied when the modification itself materially and adversely affects the operation of the network or violates the rules and protocols for communication across the network. Corresponding Source conveyed, and Installation Information provided, in accord with this section must be in a format that is publicly documented (and with an implementation available to the public in source code form), and must require no special password or key for unpacking, reading or copying. 7. Additional Terms. "Additional permissions" are terms that supplement the terms of this License by making exceptions from one or more of its conditions. Additional permissions that are applicable to the entire Program shall be treated as though they were included in this License, to the extent that they are valid under applicable law. If additional permissions apply only to part of the Program, that part may be used separately under those permissions, but the entire Program remains governed by this License without regard to the additional permissions. When you convey a copy of a covered work, you may at your option remove any additional permissions from that copy, or from any part of it. (Additional permissions may be written to require their own removal in certain cases when you modify the work.) You may place additional permissions on material, added by you to a covered work, for which you have or can give appropriate copyright permission. Notwithstanding any other provision of this License, for material you add to a covered work, you may (if authorized by the copyright holders of that material) supplement the terms of this License with terms: a) Disclaiming warranty or limiting liability differently from the terms of sections 15 and 16 of this License; or b) Requiring preservation of specified reasonable legal notices or author attributions in that material or in the Appropriate Legal Notices displayed by works containing it; or c) Prohibiting misrepresentation of the origin of that material, or requiring that modified versions of such material be marked in reasonable ways as different from the original version; or d) Limiting the use for publicity purposes of names of licensors or authors of the material; or e) Declining to grant rights under trademark law for use of some trade names, trademarks, or service marks; or f) Requiring indemnification of licensors and authors of that material by anyone who conveys the material (or modified versions of it) with contractual assumptions of liability to the recipient, for any liability that these contractual assumptions directly impose on those licensors and authors. All other non-permissive additional terms are considered "further restrictions" within the meaning of section 10. If the Program as you received it, or any part of it, contains a notice stating that it is governed by this License along with a term that is a further restriction, you may remove that term. If a license document contains a further restriction but permits relicensing or conveying under this License, you may add to a covered work material governed by the terms of that license document, provided that the further restriction does not survive such relicensing or conveying. If you add terms to a covered work in accord with this section, you must place, in the relevant source files, a statement of the additional terms that apply to those files, or a notice indicating where to find the applicable terms. Additional terms, permissive or non-permissive, may be stated in the form of a separately written license, or stated as exceptions; the above requirements apply either way. 8. Termination. You may not propagate or modify a covered work except as expressly provided under this License. Any attempt otherwise to propagate or modify it is void, and will automatically terminate your rights under this License (including any patent licenses granted under the third paragraph of section 11). However, if you cease all violation of this License, then your license from a particular copyright holder is reinstated (a) provisionally, unless and until the copyright holder explicitly and finally terminates your license, and (b) permanently, if the copyright holder fails to notify you of the violation by some reasonable means prior to 60 days after the cessation. Moreover, your license from a particular copyright holder is reinstated permanently if the copyright holder notifies you of the violation by some reasonable means, this is the first time you have received notice of violation of this License (for any work) from that copyright holder, and you cure the violation prior to 30 days after your receipt of the notice. Termination of your rights under this section does not terminate the licenses of parties who have received copies or rights from you under this License. If your rights have been terminated and not permanently reinstated, you do not qualify to receive new licenses for the same material under section 10. 9. Acceptance Not Required for Having Copies. You are not required to accept this License in order to receive or run a copy of the Program. Ancillary propagation of a covered work occurring solely as a consequence of using peer-to-peer transmission to receive a copy likewise does not require acceptance. However, nothing other than this License grants you permission to propagate or modify any covered work. These actions infringe copyright if you do not accept this License. Therefore, by modifying or propagating a covered work, you indicate your acceptance of this License to do so. 10. Automatic Licensing of Downstream Recipients. Each time you convey a covered work, the recipient automatically receives a license from the original licensors, to run, modify and propagate that work, subject to this License. You are not responsible for enforcing compliance by third parties with this License. An "entity transaction" is a transaction transferring control of an organization, or substantially all assets of one, or subdividing an organization, or merging organizations. If propagation of a covered work results from an entity transaction, each party to that transaction who receives a copy of the work also receives whatever licenses to the work the party's predecessor in interest had or could give under the previous paragraph, plus a right to possession of the Corresponding Source of the work from the predecessor in interest, if the predecessor has it or can get it with reasonable efforts. You may not impose any further restrictions on the exercise of the rights granted or affirmed under this License. For example, you may not impose a license fee, royalty, or other charge for exercise of rights granted under this License, and you may not initiate litigation (including a cross-claim or counterclaim in a lawsuit) alleging that any patent claim is infringed by making, using, selling, offering for sale, or importing the Program or any portion of it. 11. Patents. A "contributor" is a copyright holder who authorizes use under this License of the Program or a work on which the Program is based. The work thus licensed is called the contributor's "contributor version". A contributor's "essential patent claims" are all patent claims owned or controlled by the contributor, whether already acquired or hereafter acquired, that would be infringed by some manner, permitted by this License, of making, using, or selling its contributor version, but do not include claims that would be infringed only as a consequence of further modification of the contributor version. For purposes of this definition, "control" includes the right to grant patent sublicenses in a manner consistent with the requirements of this License. Each contributor grants you a non-exclusive, worldwide, royalty-free patent license under the contributor's essential patent claims, to make, use, sell, offer for sale, import and otherwise run, modify and propagate the contents of its contributor version. In the following three paragraphs, a "patent license" is any express agreement or commitment, however denominated, not to enforce a patent (such as an express permission to practice a patent or covenant not to sue for patent infringement). To "grant" such a patent license to a party means to make such an agreement or commitment not to enforce a patent against the party. If you convey a covered work, knowingly relying on a patent license, and the Corresponding Source of the work is not available for anyone to copy, free of charge and under the terms of this License, through a publicly available network server or other readily accessible means, then you must either (1) cause the Corresponding Source to be so available, or (2) arrange to deprive yourself of the benefit of the patent license for this particular work, or (3) arrange, in a manner consistent with the requirements of this License, to extend the patent license to downstream recipients. "Knowingly relying" means you have actual knowledge that, but for the patent license, your conveying the covered work in a country, or your recipient's use of the covered work in a country, would infringe one or more identifiable patents in that country that you have reason to believe are valid. If, pursuant to or in connection with a single transaction or arrangement, you convey, or propagate by procuring conveyance of, a covered work, and grant a patent license to some of the parties receiving the covered work authorizing them to use, propagate, modify or convey a specific copy of the covered work, then the patent license you grant is automatically extended to all recipients of the covered work and works based on it. A patent license is "discriminatory" if it does not include within the scope of its coverage, prohibits the exercise of, or is conditioned on the non-exercise of one or more of the rights that are specifically granted under this License. You may not convey a covered work if you are a party to an arrangement with a third party that is in the business of distributing software, under which you make payment to the third party based on the extent of your activity of conveying the work, and under which the third party grants, to any of the parties who would receive the covered work from you, a discriminatory patent license (a) in connection with copies of the covered work conveyed by you (or copies made from those copies), or (b) primarily for and in connection with specific products or compilations that contain the covered work, unless you entered into that arrangement, or that patent license was granted, prior to 28 March 2007. Nothing in this License shall be construed as excluding or limiting any implied license or other defenses to infringement that may otherwise be available to you under applicable patent law. 12. No Surrender of Others' Freedom. If conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot convey a covered work so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not convey it at all. For example, if you agree to terms that obligate you to collect a royalty for further conveying from those to whom you convey the Program, the only way you could satisfy both those terms and this License would be to refrain entirely from conveying the Program. 13. Use with the GNU Affero General Public License. Notwithstanding any other provision of this License, you have permission to link or combine any covered work with a work licensed under version 3 of the GNU Affero General Public License into a single combined work, and to convey the resulting work. The terms of this License will continue to apply to the part which is the covered work, but the special requirements of the GNU Affero General Public License, section 13, concerning interaction through a network will apply to the combination as such. 14. Revised Versions of this License. The Free Software Foundation may publish revised and/or new versions of the GNU General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns. Each version is given a distinguishing version number. If the Program specifies that a certain numbered version of the GNU General Public License "or any later version" applies to it, you have the option of following the terms and conditions either of that numbered version or of any later version published by the Free Software Foundation. If the Program does not specify a version number of the GNU General Public License, you may choose any version ever published by the Free Software Foundation. If the Program specifies that a proxy can decide which future versions of the GNU General Public License can be used, that proxy's public statement of acceptance of a version permanently authorizes you to choose that version for the Program. Later license versions may give you additional or different permissions. However, no additional obligations are imposed on any author or copyright holder as a result of your choosing to follow a later version. 15. Disclaimer of Warranty. THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 16. Limitation of Liability. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. 17. Interpretation of Sections 15 and 16. If the disclaimer of warranty and limitation of liability provided above cannot be given local legal effect according to their terms, reviewing courts shall apply local law that most closely approximates an absolute waiver of all civil liability in connection with the Program, unless a warranty or assumption of liability accompanies a copy of the Program in return for a fee. END OF TERMS AND CONDITIONS How to Apply These Terms to Your New Programs If you develop a new program, and you want it to be of the greatest possible use to the public, the best way to achieve this is to make it free software which everyone can redistribute and change under these terms. To do so, attach the following notices to the program. It is safest to attach them to the start of each source file to most effectively state the exclusion of warranty; and each file should have at least the "copyright" line and a pointer to where the full notice is found. Copyright (C) This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . Also add information on how to contact you by electronic and paper mail. If the program does terminal interaction, make it output a short notice like this when it starts in an interactive mode: Copyright (C) This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'. This is free software, and you are welcome to redistribute it under certain conditions; type `show c' for details. The hypothetical commands `show w' and `show c' should show the appropriate parts of the General Public License. Of course, your program's commands might be different; for a GUI interface, you would use an "about box". You should also get your employer (if you work as a programmer) or school, if any, to sign a "copyright disclaimer" for the program, if necessary. For more information on this, and how to apply and follow the GNU GPL, see . The GNU General Public License does not permit incorporating your program into proprietary programs. If your program is a subroutine library, you may consider it more useful to permit linking proprietary applications with the library. If this is what you want to do, use the GNU Lesser General Public License instead of this License. But first, please read . ================================================ FILE: makelinks.bat ================================================ @echo off set path_w32d=%~dp0bin\win32\debug\ set path_w32r=%~dp0bin\win32\release\ set path_w32p=%~dp0bin\win32\releasep\ set path_x64d=%~dp0bin\x64\debug\ set path_x64r=%~dp0bin\x64\release\ set path_x64p=%~dp0bin\x64\releasep\ set path_trans_l=%~dp0etc\translations\software\ set path_trans_h=%~dp0etc\translations\help\ set path_cdrtools=%~dp0dep\cdrtools\ set path_sndfile=%~dp0dep\libsndfile\ set path_smoke=%~dp0dep\ set path_help=%~dp0doc\english\ rem make sure directories exists. if not exist %path_w32d%codecs\ mkdir %path_w32d%codecs\ if not exist %path_w32r%codecs\ mkdir %path_w32r%codecs\ if not exist %path_w32p%codecs\ mkdir %path_w32p%codecs\ if not exist %path_x64d%codecs\ mkdir %path_x64d%codecs\ if not exist %path_x64r%codecs\ mkdir %path_x64r%codecs\ if not exist %path_x64p%codecs\ mkdir %path_x64p%codecs\ if not exist %path_w32d%languages\ mkdir %path_w32d%languages\ if not exist %path_w32r%languages\ mkdir %path_w32r%languages\ if not exist %path_w32p%languages\ mkdir %path_w32p%languages\ if not exist %path_x64d%languages\ mkdir %path_x64d%languages\ if not exist %path_x64r%languages\ mkdir %path_x64r%languages\ if not exist %path_x64p%languages\ mkdir %path_x64p%languages\ rem make symbolic links to cdrtools binaries. if not exist %path_w32d%cdrtools mklink /D %path_w32d%cdrtools %path_cdrtools% if not exist %path_w32r%cdrtools mklink /D %path_w32r%cdrtools %path_cdrtools% if not exist %path_w32p%cdrtools mklink /D %path_w32p%cdrtools %path_cdrtools% if not exist %path_x64d%cdrtools mklink /D %path_x64d%cdrtools %path_cdrtools% if not exist %path_x64r%cdrtools mklink /D %path_x64r%cdrtools %path_cdrtools% if not exist %path_x64p%cdrtools mklink /D %path_x64p%cdrtools %path_cdrtools% rem make symbolic links to libsndfile libraries. if not exist %path_w32d%codecs\libsndfile-1.dll mklink %path_w32d%codecs\libsndfile-1.dll %path_sndfile%win32\libsndfile-1.dll if not exist %path_w32r%codecs\libsndfile-1.dll mklink %path_w32r%codecs\libsndfile-1.dll %path_sndfile%win32\libsndfile-1.dll if not exist %path_w32p%codecs\libsndfile-1.dll mklink %path_w32p%codecs\libsndfile-1.dll %path_sndfile%win32\libsndfile-1.dll if not exist %path_x64d%codecs\libsndfile-1.dll mklink %path_x64d%codecs\libsndfile-1.dll %path_sndfile%x64\libsndfile-1.dll if not exist %path_x64r%codecs\libsndfile-1.dll mklink %path_x64r%codecs\libsndfile-1.dll %path_sndfile%x64\libsndfile-1.dll if not exist %path_x64p%codecs\libsndfile-1.dll mklink %path_x64p%codecs\libsndfile-1.dll %path_sndfile%x64\libsndfile-1.dll rem make symbolic links to smoke program. if not exist %path_w32d%smoke.exe mklink %path_w32d%smoke.exe %path_smoke%smoke.exe if not exist %path_w32r%smoke.exe mklink %path_w32r%smoke.exe %path_smoke%smoke.exe if not exist %path_w32p%smoke.exe mklink %path_w32p%smoke.exe %path_smoke%smoke.exe if not exist %path_x64d%smoke.exe mklink %path_x64d%smoke.exe %path_smoke%smoke.exe if not exist %path_x64r%smoke.exe mklink %path_x64r%smoke.exe %path_smoke%smoke.exe if not exist %path_x64p%smoke.exe mklink %path_x64p%smoke.exe %path_smoke%smoke.exe rem make symbolic links to help file. if not exist %path_w32d%infrarecorder.chm mklink %path_w32d%infrarecorder.chm %path_help%infrarecorder.chm if not exist %path_w32r%infrarecorder.chm mklink %path_w32r%infrarecorder.chm %path_help%infrarecorder.chm if not exist %path_w32p%infrarecorder.chm mklink %path_w32p%infrarecorder.chm %path_help%infrarecorder.chm if not exist %path_x64d%infrarecorder.chm mklink %path_x64d%infrarecorder.chm %path_help%infrarecorder.chm if not exist %path_x64r%infrarecorder.chm mklink %path_x64r%infrarecorder.chm %path_help%infrarecorder.chm if not exist %path_x64p%infrarecorder.chm mklink %path_x64p%infrarecorder.chm %path_help%infrarecorder.chm rem make symbolic links to translations. if not exist %path_w32d%languages\albanian.irl mklink %path_w32d%languages\albanian.irl %path_trans_l%albanian.irl if not exist %path_w32d%languages\arabic.irl mklink %path_w32d%languages\arabic.irl %path_trans_l%arabic.irl if not exist %path_w32d%languages\armenian.irl mklink %path_w32d%languages\armenian.irl %path_trans_l%armenian.irl if not exist %path_w32d%languages\basque.irl mklink %path_w32d%languages\basque.irl %path_trans_l%basque.irl if not exist %path_w32d%languages\bosnian.irl mklink %path_w32d%languages\bosnian.irl %path_trans_l%bosnian.irl if not exist %path_w32d%languages\bulgarian.irl mklink %path_w32d%languages\bulgarian.irl %path_trans_l%bulgarian.irl if not exist %path_w32d%languages\catalan.irl mklink %path_w32d%languages\catalan.irl %path_trans_l%catalan.irl if not exist %path_w32d%languages\chinese-simplified.irl mklink %path_w32d%languages\chinese-simplified.irl %path_trans_l%chinese-simplified.irl if not exist %path_w32d%languages\chinese-traditional.irl mklink %path_w32d%languages\chinese-traditional.irl %path_trans_l%chinese-traditional.irl if not exist %path_w32d%languages\chuvash.irl mklink %path_w32d%languages\chuvash.irl %path_trans_l%chuvash.irl if not exist %path_w32d%languages\croatian.irl mklink %path_w32d%languages\croatian.irl %path_trans_l%croatian.irl if not exist %path_w32d%languages\czech.irl mklink %path_w32d%languages\czech.irl %path_trans_l%czech.irl if not exist %path_w32d%languages\danish.irl mklink %path_w32d%languages\danish.irl %path_trans_l%danish.irl if not exist %path_w32d%languages\dutch.irl mklink %path_w32d%languages\dutch.irl %path_trans_l%dutch.irl if not exist %path_w32d%languages\estonian.irl mklink %path_w32d%languages\estonian.irl %path_trans_l%estonian.irl if not exist %path_w32d%languages\farsi.irl mklink %path_w32d%languages\farsi.irl %path_trans_l%farsi.irl if not exist %path_w32d%languages\finnish.irl mklink %path_w32d%languages\finnish.irl %path_trans_l%finnish.irl if not exist %path_w32d%languages\french.irl mklink %path_w32d%languages\french.irl %path_trans_l%french.irl if not exist %path_w32d%languages\galician.irl mklink %path_w32d%languages\galician.irl %path_trans_l%galician.irl if not exist %path_w32d%languages\german.irl mklink %path_w32d%languages\german.irl %path_trans_l%german.irl if not exist %path_w32d%languages\georgian.irl mklink %path_w32d%languages\georgian.irl %path_trans_l%georgian.irl if not exist %path_w32d%languages\greek.irl mklink %path_w32d%languages\greek.irl %path_trans_l%greek.irl if not exist %path_w32d%languages\hebrew.irl mklink %path_w32d%languages\hebrew.irl %path_trans_l%hebrew.irl if not exist %path_w32d%languages\hungarian.irl mklink %path_w32d%languages\hungarian.irl %path_trans_l%hungarian.irl if not exist %path_w32d%languages\indonesian.irl mklink %path_w32d%languages\indonesian.irl %path_trans_l%indonesian.irl if not exist %path_w32d%languages\italian.irl mklink %path_w32d%languages\italian.irl %path_trans_l%italian.irl if not exist %path_w32d%languages\japanese.irl mklink %path_w32d%languages\japanese.irl %path_trans_l%japanese.irl if not exist %path_w32d%languages\korean.irl mklink %path_w32d%languages\korean.irl %path_trans_l%korean.irl if not exist %path_w32d%languages\latvian.irl mklink %path_w32d%languages\latvian.irl %path_trans_l%latvian.irl if not exist %path_w32d%languages\lithuanian.irl mklink %path_w32d%languages\lithuanian.irl %path_trans_l%lithuanian.irl if not exist %path_w32d%languages\macedonian.irl mklink %path_w32d%languages\macedonian.irl %path_trans_l%macedonian.irl if not exist %path_w32d%languages\norwegian.irl mklink %path_w32d%languages\norwegian.irl %path_trans_l%norwegian.irl if not exist %path_w32d%languages\polish.irl mklink %path_w32d%languages\polish.irl %path_trans_l%polish.irl if not exist %path_w32d%languages\portuguese.irl mklink %path_w32d%languages\portuguese.irl %path_trans_l%portuguese.irl if not exist %path_w32d%languages\portuguese-brazilian.irl mklink %path_w32d%languages\portuguese-brazilian.irl %path_trans_l%portuguese-brazilian.irl if not exist %path_w32d%languages\romanian.irl mklink %path_w32d%languages\romanian.irl %path_trans_l%romanian.irl if not exist %path_w32d%languages\russian.irl mklink %path_w32d%languages\russian.irl %path_trans_l%russian.irl if not exist %path_w32d%languages\serbian-cyrillic.irl mklink %path_w32d%languages\serbian-cyrillic.irl %path_trans_l%serbian-cyrillic.irl if not exist %path_w32d%languages\serbian-latin.irl mklink %path_w32d%languages\serbian-latin.irl %path_trans_l%serbian-latin.irl if not exist %path_w32d%languages\slovak.irl mklink %path_w32d%languages\slovak.irl %path_trans_l%slovak.irl if not exist %path_w32d%languages\slovenian.irl mklink %path_w32d%languages\slovenian.irl %path_trans_l%slovenian.irl if not exist %path_w32d%languages\spanish.irl mklink %path_w32d%languages\spanish.irl %path_trans_l%spanish.irl if not exist %path_w32d%languages\swedish.irl mklink %path_w32d%languages\swedish.irl %path_trans_l%swedish.irl if not exist %path_w32d%languages\thai.irl mklink %path_w32d%languages\thai.irl %path_trans_l%thai.irl if not exist %path_w32d%languages\turkish.irl mklink %path_w32d%languages\turkish.irl %path_trans_l%turkish.irl if not exist %path_w32d%languages\ukrainian.irl mklink %path_w32d%languages\ukrainian.irl %path_trans_l%ukrainian.irl if not exist %path_w32d%languages\valencian.irl mklink %path_w32d%languages\valencian.irl %path_trans_l%valencian.irl if not exist %path_w32d%languages\vietnamese.irl mklink %path_w32d%languages\vietnamese.irl %path_trans_l%vietnamese.irl if not exist %path_w32r%languages\albanian.irl mklink %path_w32r%languages\albanian.irl %path_trans_l%albanian.irl if not exist %path_w32r%languages\arabic.irl mklink %path_w32r%languages\arabic.irl %path_trans_l%arabic.irl if not exist %path_w32r%languages\armenian.irl mklink %path_w32r%languages\armenian.irl %path_trans_l%armenian.irl if not exist %path_w32r%languages\basque.irl mklink %path_w32r%languages\basque.irl %path_trans_l%basque.irl if not exist %path_w32r%languages\bosnian.irl mklink %path_w32r%languages\bosnian.irl %path_trans_l%bosnian.irl if not exist %path_w32r%languages\bulgarian.irl mklink %path_w32r%languages\bulgarian.irl %path_trans_l%bulgarian.irl if not exist %path_w32r%languages\catalan.irl mklink %path_w32r%languages\catalan.irl %path_trans_l%catalan.irl if not exist %path_w32r%languages\chinese-simplified.irl mklink %path_w32r%languages\chinese-simplified.irl %path_trans_l%chinese-simplified.irl if not exist %path_w32r%languages\chinese-traditional.irl mklink %path_w32r%languages\chinese-traditional.irl %path_trans_l%chinese-traditional.irl if not exist %path_w32r%languages\chuvash.irl mklink %path_w32r%languages\chuvash.irl %path_trans_l%chuvash.irl if not exist %path_w32r%languages\croatian.irl mklink %path_w32r%languages\croatian.irl %path_trans_l%croatian.irl if not exist %path_w32r%languages\czech.irl mklink %path_w32r%languages\czech.irl %path_trans_l%czech.irl if not exist %path_w32r%languages\danish.irl mklink %path_w32r%languages\danish.irl %path_trans_l%danish.irl if not exist %path_w32r%languages\dutch.irl mklink %path_w32r%languages\dutch.irl %path_trans_l%dutch.irl if not exist %path_w32r%languages\estonian.irl mklink %path_w32r%languages\estonian.irl %path_trans_l%estonian.irl if not exist %path_w32r%languages\farsi.irl mklink %path_w32r%languages\farsi.irl %path_trans_l%farsi.irl if not exist %path_w32r%languages\finnish.irl mklink %path_w32r%languages\finnish.irl %path_trans_l%finnish.irl if not exist %path_w32r%languages\french.irl mklink %path_w32r%languages\french.irl %path_trans_l%french.irl if not exist %path_w32r%languages\galician.irl mklink %path_w32r%languages\galician.irl %path_trans_l%galician.irl if not exist %path_w32r%languages\german.irl mklink %path_w32r%languages\german.irl %path_trans_l%german.irl if not exist %path_w32r%languages\georgian.irl mklink %path_w32r%languages\georgian.irl %path_trans_l%georgian.irl if not exist %path_w32r%languages\greek.irl mklink %path_w32r%languages\greek.irl %path_trans_l%greek.irl if not exist %path_w32r%languages\hebrew.irl mklink %path_w32r%languages\hebrew.irl %path_trans_l%hebrew.irl if not exist %path_w32r%languages\hungarian.irl mklink %path_w32r%languages\hungarian.irl %path_trans_l%hungarian.irl if not exist %path_w32r%languages\indonesian.irl mklink %path_w32r%languages\indonesian.irl %path_trans_l%indonesian.irl if not exist %path_w32r%languages\italian.irl mklink %path_w32r%languages\italian.irl %path_trans_l%italian.irl if not exist %path_w32r%languages\japanese.irl mklink %path_w32r%languages\japanese.irl %path_trans_l%japanese.irl if not exist %path_w32r%languages\korean.irl mklink %path_w32r%languages\korean.irl %path_trans_l%korean.irl if not exist %path_w32r%languages\latvian.irl mklink %path_w32r%languages\latvian.irl %path_trans_l%latvian.irl if not exist %path_w32r%languages\lithuanian.irl mklink %path_w32r%languages\lithuanian.irl %path_trans_l%lithuanian.irl if not exist %path_w32r%languages\macedonian.irl mklink %path_w32r%languages\macedonian.irl %path_trans_l%macedonian.irl if not exist %path_w32r%languages\norwegian.irl mklink %path_w32r%languages\norwegian.irl %path_trans_l%norwegian.irl if not exist %path_w32r%languages\polish.irl mklink %path_w32r%languages\polish.irl %path_trans_l%polish.irl if not exist %path_w32r%languages\portuguese.irl mklink %path_w32r%languages\portuguese.irl %path_trans_l%portuguese.irl if not exist %path_w32r%languages\portuguese-brazilian.irl mklink %path_w32r%languages\portuguese-brazilian.irl %path_trans_l%portuguese-brazilian.irl if not exist %path_w32r%languages\romanian.irl mklink %path_w32r%languages\romanian.irl %path_trans_l%romanian.irl if not exist %path_w32r%languages\russian.irl mklink %path_w32r%languages\russian.irl %path_trans_l%russian.irl if not exist %path_w32r%languages\serbian-cyrillic.irl mklink %path_w32r%languages\serbian-cyrillic.irl %path_trans_l%serbian-cyrillic.irl if not exist %path_w32r%languages\serbian-latin.irl mklink %path_w32r%languages\serbian-latin.irl %path_trans_l%serbian-latin.irl if not exist %path_w32r%languages\slovak.irl mklink %path_w32r%languages\slovak.irl %path_trans_l%slovak.irl if not exist %path_w32r%languages\slovenian.irl mklink %path_w32r%languages\slovenian.irl %path_trans_l%slovenian.irl if not exist %path_w32r%languages\spanish.irl mklink %path_w32r%languages\spanish.irl %path_trans_l%spanish.irl if not exist %path_w32r%languages\swedish.irl mklink %path_w32r%languages\swedish.irl %path_trans_l%swedish.irl if not exist %path_w32r%languages\thai.irl mklink %path_w32r%languages\thai.irl %path_trans_l%thai.irl if not exist %path_w32r%languages\turkish.irl mklink %path_w32r%languages\turkish.irl %path_trans_l%turkish.irl if not exist %path_w32r%languages\ukrainian.irl mklink %path_w32r%languages\ukrainian.irl %path_trans_l%ukrainian.irl if not exist %path_w32r%languages\valencian.irl mklink %path_w32r%languages\valencian.irl %path_trans_l%valencian.irl if not exist %path_w32r%languages\vietnamese.irl mklink %path_w32r%languages\vietnamese.irl %path_trans_l%vietnamese.irl if not exist %path_w32p%languages\albanian.irl mklink %path_w32p%languages\albanian.irl %path_trans_l%albanian.irl if not exist %path_w32p%languages\arabic.irl mklink %path_w32p%languages\arabic.irl %path_trans_l%arabic.irl if not exist %path_w32p%languages\armenian.irl mklink %path_w32p%languages\armenian.irl %path_trans_l%armenian.irl if not exist %path_w32p%languages\basque.irl mklink %path_w32p%languages\basque.irl %path_trans_l%basque.irl if not exist %path_w32p%languages\bosnian.irl mklink %path_w32p%languages\bosnian.irl %path_trans_l%bosnian.irl if not exist %path_w32p%languages\bulgarian.irl mklink %path_w32p%languages\bulgarian.irl %path_trans_l%bulgarian.irl if not exist %path_w32p%languages\catalan.irl mklink %path_w32p%languages\catalan.irl %path_trans_l%catalan.irl if not exist %path_w32p%languages\chinese-simplified.irl mklink %path_w32p%languages\chinese-simplified.irl %path_trans_l%chinese-simplified.irl if not exist %path_w32p%languages\chinese-traditional.irl mklink %path_w32p%languages\chinese-traditional.irl %path_trans_l%chinese-traditional.irl if not exist %path_w32p%languages\chuvash.irl mklink %path_w32p%languages\chuvash.irl %path_trans_l%chuvash.irl if not exist %path_w32p%languages\croatian.irl mklink %path_w32p%languages\croatian.irl %path_trans_l%croatian.irl if not exist %path_w32p%languages\czech.irl mklink %path_w32p%languages\czech.irl %path_trans_l%czech.irl if not exist %path_w32p%languages\danish.irl mklink %path_w32p%languages\danish.irl %path_trans_l%danish.irl if not exist %path_w32p%languages\dutch.irl mklink %path_w32p%languages\dutch.irl %path_trans_l%dutch.irl if not exist %path_w32p%languages\estonian.irl mklink %path_w32p%languages\estonian.irl %path_trans_l%estonian.irl if not exist %path_w32p%languages\farsi.irl mklink %path_w32p%languages\farsi.irl %path_trans_l%farsi.irl if not exist %path_w32p%languages\finnish.irl mklink %path_w32p%languages\finnish.irl %path_trans_l%finnish.irl if not exist %path_w32p%languages\french.irl mklink %path_w32p%languages\french.irl %path_trans_l%french.irl if not exist %path_w32p%languages\galician.irl mklink %path_w32p%languages\galician.irl %path_trans_l%galician.irl if not exist %path_w32p%languages\german.irl mklink %path_w32p%languages\german.irl %path_trans_l%german.irl if not exist %path_w32p%languages\georgian.irl mklink %path_w32p%languages\georgian.irl %path_trans_l%georgian.irl if not exist %path_w32p%languages\greek.irl mklink %path_w32p%languages\greek.irl %path_trans_l%greek.irl if not exist %path_w32p%languages\hebrew.irl mklink %path_w32p%languages\hebrew.irl %path_trans_l%hebrew.irl if not exist %path_w32p%languages\hungarian.irl mklink %path_w32p%languages\hungarian.irl %path_trans_l%hungarian.irl if not exist %path_w32p%languages\indonesian.irl mklink %path_w32p%languages\indonesian.irl %path_trans_l%indonesian.irl if not exist %path_w32p%languages\italian.irl mklink %path_w32p%languages\italian.irl %path_trans_l%italian.irl if not exist %path_w32p%languages\japanese.irl mklink %path_w32p%languages\japanese.irl %path_trans_l%japanese.irl if not exist %path_w32p%languages\korean.irl mklink %path_w32p%languages\korean.irl %path_trans_l%korean.irl if not exist %path_w32p%languages\latvian.irl mklink %path_w32p%languages\latvian.irl %path_trans_l%latvian.irl if not exist %path_w32p%languages\lithuanian.irl mklink %path_w32p%languages\lithuanian.irl %path_trans_l%lithuanian.irl if not exist %path_w32p%languages\macedonian.irl mklink %path_w32p%languages\macedonian.irl %path_trans_l%macedonian.irl if not exist %path_w32p%languages\norwegian.irl mklink %path_w32p%languages\norwegian.irl %path_trans_l%norwegian.irl if not exist %path_w32p%languages\polish.irl mklink %path_w32p%languages\polish.irl %path_trans_l%polish.irl if not exist %path_w32p%languages\portuguese.irl mklink %path_w32p%languages\portuguese.irl %path_trans_l%portuguese.irl if not exist %path_w32p%languages\portuguese-brazilian.irl mklink %path_w32p%languages\portuguese-brazilian.irl %path_trans_l%portuguese-brazilian.irl if not exist %path_w32p%languages\romanian.irl mklink %path_w32p%languages\romanian.irl %path_trans_l%romanian.irl if not exist %path_w32p%languages\russian.irl mklink %path_w32p%languages\russian.irl %path_trans_l%russian.irl if not exist %path_w32p%languages\serbian-cyrillic.irl mklink %path_w32p%languages\serbian-cyrillic.irl %path_trans_l%serbian-cyrillic.irl if not exist %path_w32p%languages\serbian-latin.irl mklink %path_w32p%languages\serbian-latin.irl %path_trans_l%serbian-latin.irl if not exist %path_w32p%languages\slovak.irl mklink %path_w32p%languages\slovak.irl %path_trans_l%slovak.irl if not exist %path_w32p%languages\slovenian.irl mklink %path_w32p%languages\slovenian.irl %path_trans_l%slovenian.irl if not exist %path_w32p%languages\spanish.irl mklink %path_w32p%languages\spanish.irl %path_trans_l%spanish.irl if not exist %path_w32p%languages\swedish.irl mklink %path_w32p%languages\swedish.irl %path_trans_l%swedish.irl if not exist %path_w32p%languages\thai.irl mklink %path_w32p%languages\thai.irl %path_trans_l%thai.irl if not exist %path_w32p%languages\turkish.irl mklink %path_w32p%languages\turkish.irl %path_trans_l%turkish.irl if not exist %path_w32p%languages\ukrainian.irl mklink %path_w32p%languages\ukrainian.irl %path_trans_l%ukrainian.irl if not exist %path_w32p%languages\valencian.irl mklink %path_w32p%languages\valencian.irl %path_trans_l%valencian.irl if not exist %path_w32p%languages\vietnamese.irl mklink %path_w32p%languages\vietnamese.irl %path_trans_l%vietnamese.irl if not exist %path_x64d%languages\albanian.irl mklink %path_x64d%languages\albanian.irl %path_trans_l%albanian.irl if not exist %path_x64d%languages\arabic.irl mklink %path_x64d%languages\arabic.irl %path_trans_l%arabic.irl if not exist %path_x64d%languages\armenian.irl mklink %path_x64d%languages\armenian.irl %path_trans_l%armenian.irl if not exist %path_x64d%languages\basque.irl mklink %path_x64d%languages\basque.irl %path_trans_l%basque.irl if not exist %path_x64d%languages\bosnian.irl mklink %path_x64d%languages\bosnian.irl %path_trans_l%bosnian.irl if not exist %path_x64d%languages\bulgarian.irl mklink %path_x64d%languages\bulgarian.irl %path_trans_l%bulgarian.irl if not exist %path_x64d%languages\catalan.irl mklink %path_x64d%languages\catalan.irl %path_trans_l%catalan.irl if not exist %path_x64d%languages\chinese-simplified.irl mklink %path_x64d%languages\chinese-simplified.irl %path_trans_l%chinese-simplified.irl if not exist %path_x64d%languages\chinese-traditional.irl mklink %path_x64d%languages\chinese-traditional.irl %path_trans_l%chinese-traditional.irl if not exist %path_x64d%languages\chuvash.irl mklink %path_x64d%languages\chuvash.irl %path_trans_l%chuvash.irl if not exist %path_x64d%languages\croatian.irl mklink %path_x64d%languages\croatian.irl %path_trans_l%croatian.irl if not exist %path_x64d%languages\czech.irl mklink %path_x64d%languages\czech.irl %path_trans_l%czech.irl if not exist %path_x64d%languages\danish.irl mklink %path_x64d%languages\danish.irl %path_trans_l%danish.irl if not exist %path_x64d%languages\dutch.irl mklink %path_x64d%languages\dutch.irl %path_trans_l%dutch.irl if not exist %path_x64d%languages\estonian.irl mklink %path_x64d%languages\estonian.irl %path_trans_l%estonian.irl if not exist %path_x64d%languages\farsi.irl mklink %path_x64d%languages\farsi.irl %path_trans_l%farsi.irl if not exist %path_x64d%languages\finnish.irl mklink %path_x64d%languages\finnish.irl %path_trans_l%finnish.irl if not exist %path_x64d%languages\french.irl mklink %path_x64d%languages\french.irl %path_trans_l%french.irl if not exist %path_x64d%languages\galician.irl mklink %path_x64d%languages\galician.irl %path_trans_l%galician.irl if not exist %path_x64d%languages\german.irl mklink %path_x64d%languages\german.irl %path_trans_l%german.irl if not exist %path_x64d%languages\georgian.irl mklink %path_x64d%languages\georgian.irl %path_trans_l%georgian.irl if not exist %path_x64d%languages\greek.irl mklink %path_x64d%languages\greek.irl %path_trans_l%greek.irl if not exist %path_x64d%languages\hebrew.irl mklink %path_x64d%languages\hebrew.irl %path_trans_l%hebrew.irl if not exist %path_x64d%languages\hungarian.irl mklink %path_x64d%languages\hungarian.irl %path_trans_l%hungarian.irl if not exist %path_x64d%languages\indonesian.irl mklink %path_x64d%languages\indonesian.irl %path_trans_l%indonesian.irl if not exist %path_x64d%languages\italian.irl mklink %path_x64d%languages\italian.irl %path_trans_l%italian.irl if not exist %path_x64d%languages\japanese.irl mklink %path_x64d%languages\japanese.irl %path_trans_l%japanese.irl if not exist %path_x64d%languages\korean.irl mklink %path_x64d%languages\korean.irl %path_trans_l%korean.irl if not exist %path_x64d%languages\latvian.irl mklink %path_x64d%languages\latvian.irl %path_trans_l%latvian.irl if not exist %path_x64d%languages\lithuanian.irl mklink %path_x64d%languages\lithuanian.irl %path_trans_l%lithuanian.irl if not exist %path_x64d%languages\macedonian.irl mklink %path_x64d%languages\macedonian.irl %path_trans_l%macedonian.irl if not exist %path_x64d%languages\norwegian.irl mklink %path_x64d%languages\norwegian.irl %path_trans_l%norwegian.irl if not exist %path_x64d%languages\polish.irl mklink %path_x64d%languages\polish.irl %path_trans_l%polish.irl if not exist %path_x64d%languages\portuguese.irl mklink %path_x64d%languages\portuguese.irl %path_trans_l%portuguese.irl if not exist %path_x64d%languages\portuguese-brazilian.irl mklink %path_x64d%languages\portuguese-brazilian.irl %path_trans_l%portuguese-brazilian.irl if not exist %path_x64d%languages\romanian.irl mklink %path_x64d%languages\romanian.irl %path_trans_l%romanian.irl if not exist %path_x64d%languages\russian.irl mklink %path_x64d%languages\russian.irl %path_trans_l%russian.irl if not exist %path_x64d%languages\serbian-cyrillic.irl mklink %path_x64d%languages\serbian-cyrillic.irl %path_trans_l%serbian-cyrillic.irl if not exist %path_x64d%languages\serbian-latin.irl mklink %path_x64d%languages\serbian-latin.irl %path_trans_l%serbian-latin.irl if not exist %path_x64d%languages\slovak.irl mklink %path_x64d%languages\slovak.irl %path_trans_l%slovak.irl if not exist %path_x64d%languages\slovenian.irl mklink %path_x64d%languages\slovenian.irl %path_trans_l%slovenian.irl if not exist %path_x64d%languages\spanish.irl mklink %path_x64d%languages\spanish.irl %path_trans_l%spanish.irl if not exist %path_x64d%languages\swedish.irl mklink %path_x64d%languages\swedish.irl %path_trans_l%swedish.irl if not exist %path_x64d%languages\thai.irl mklink %path_x64d%languages\thai.irl %path_trans_l%thai.irl if not exist %path_x64d%languages\turkish.irl mklink %path_x64d%languages\turkish.irl %path_trans_l%turkish.irl if not exist %path_x64d%languages\ukrainian.irl mklink %path_x64d%languages\ukrainian.irl %path_trans_l%ukrainian.irl if not exist %path_x64d%languages\valencian.irl mklink %path_x64d%languages\valencian.irl %path_trans_l%valencian.irl if not exist %path_x64d%languages\vietnamese.irl mklink %path_x64d%languages\vietnamese.irl %path_trans_l%vietnamese.irl if not exist %path_x64r%languages\albanian.irl mklink %path_x64r%languages\albanian.irl %path_trans_l%albanian.irl if not exist %path_x64r%languages\arabic.irl mklink %path_x64r%languages\arabic.irl %path_trans_l%arabic.irl if not exist %path_x64r%languages\armenian.irl mklink %path_x64r%languages\armenian.irl %path_trans_l%armenian.irl if not exist %path_x64r%languages\basque.irl mklink %path_x64r%languages\basque.irl %path_trans_l%basque.irl if not exist %path_x64r%languages\bosnian.irl mklink %path_x64r%languages\bosnian.irl %path_trans_l%bosnian.irl if not exist %path_x64r%languages\bulgarian.irl mklink %path_x64r%languages\bulgarian.irl %path_trans_l%bulgarian.irl if not exist %path_x64r%languages\catalan.irl mklink %path_x64r%languages\catalan.irl %path_trans_l%catalan.irl if not exist %path_x64r%languages\chinese-simplified.irl mklink %path_x64r%languages\chinese-simplified.irl %path_trans_l%chinese-simplified.irl if not exist %path_x64r%languages\chinese-traditional.irl mklink %path_x64r%languages\chinese-traditional.irl %path_trans_l%chinese-traditional.irl if not exist %path_x64r%languages\chuvash.irl mklink %path_x64r%languages\chuvash.irl %path_trans_l%chuvash.irl if not exist %path_x64r%languages\croatian.irl mklink %path_x64r%languages\croatian.irl %path_trans_l%croatian.irl if not exist %path_x64r%languages\czech.irl mklink %path_x64r%languages\czech.irl %path_trans_l%czech.irl if not exist %path_x64r%languages\danish.irl mklink %path_x64r%languages\danish.irl %path_trans_l%danish.irl if not exist %path_x64r%languages\dutch.irl mklink %path_x64r%languages\dutch.irl %path_trans_l%dutch.irl if not exist %path_x64r%languages\estonian.irl mklink %path_x64r%languages\estonian.irl %path_trans_l%estonian.irl if not exist %path_x64r%languages\farsi.irl mklink %path_x64r%languages\farsi.irl %path_trans_l%farsi.irl if not exist %path_x64r%languages\finnish.irl mklink %path_x64r%languages\finnish.irl %path_trans_l%finnish.irl if not exist %path_x64r%languages\french.irl mklink %path_x64r%languages\french.irl %path_trans_l%french.irl if not exist %path_x64r%languages\galician.irl mklink %path_x64r%languages\galician.irl %path_trans_l%galician.irl if not exist %path_x64r%languages\german.irl mklink %path_x64r%languages\german.irl %path_trans_l%german.irl if not exist %path_x64r%languages\georgian.irl mklink %path_x64r%languages\georgian.irl %path_trans_l%georgian.irl if not exist %path_x64r%languages\greek.irl mklink %path_x64r%languages\greek.irl %path_trans_l%greek.irl if not exist %path_x64r%languages\hebrew.irl mklink %path_x64r%languages\hebrew.irl %path_trans_l%hebrew.irl if not exist %path_x64r%languages\hungarian.irl mklink %path_x64r%languages\hungarian.irl %path_trans_l%hungarian.irl if not exist %path_x64r%languages\indonesian.irl mklink %path_x64r%languages\indonesian.irl %path_trans_l%indonesian.irl if not exist %path_x64r%languages\italian.irl mklink %path_x64r%languages\italian.irl %path_trans_l%italian.irl if not exist %path_x64r%languages\japanese.irl mklink %path_x64r%languages\japanese.irl %path_trans_l%japanese.irl if not exist %path_x64r%languages\korean.irl mklink %path_x64r%languages\korean.irl %path_trans_l%korean.irl if not exist %path_x64r%languages\latvian.irl mklink %path_x64r%languages\latvian.irl %path_trans_l%latvian.irl if not exist %path_x64r%languages\lithuanian.irl mklink %path_x64r%languages\lithuanian.irl %path_trans_l%lithuanian.irl if not exist %path_x64r%languages\macedonian.irl mklink %path_x64r%languages\macedonian.irl %path_trans_l%macedonian.irl if not exist %path_x64r%languages\norwegian.irl mklink %path_x64r%languages\norwegian.irl %path_trans_l%norwegian.irl if not exist %path_x64r%languages\polish.irl mklink %path_x64r%languages\polish.irl %path_trans_l%polish.irl if not exist %path_x64r%languages\portuguese.irl mklink %path_x64r%languages\portuguese.irl %path_trans_l%portuguese.irl if not exist %path_x64r%languages\portuguese-brazilian.irl mklink %path_x64r%languages\portuguese-brazilian.irl %path_trans_l%portuguese-brazilian.irl if not exist %path_x64r%languages\romanian.irl mklink %path_x64r%languages\romanian.irl %path_trans_l%romanian.irl if not exist %path_x64r%languages\russian.irl mklink %path_x64r%languages\russian.irl %path_trans_l%russian.irl if not exist %path_x64r%languages\serbian-cyrillic.irl mklink %path_x64r%languages\serbian-cyrillic.irl %path_trans_l%serbian-cyrillic.irl if not exist %path_x64r%languages\serbian-latin.irl mklink %path_x64r%languages\serbian-latin.irl %path_trans_l%serbian-latin.irl if not exist %path_x64r%languages\slovak.irl mklink %path_x64r%languages\slovak.irl %path_trans_l%slovak.irl if not exist %path_x64r%languages\slovenian.irl mklink %path_x64r%languages\slovenian.irl %path_trans_l%slovenian.irl if not exist %path_x64r%languages\spanish.irl mklink %path_x64r%languages\spanish.irl %path_trans_l%spanish.irl if not exist %path_x64r%languages\swedish.irl mklink %path_x64r%languages\swedish.irl %path_trans_l%swedish.irl if not exist %path_x64r%languages\thai.irl mklink %path_x64r%languages\thai.irl %path_trans_l%thai.irl if not exist %path_x64r%languages\turkish.irl mklink %path_x64r%languages\turkish.irl %path_trans_l%turkish.irl if not exist %path_x64r%languages\ukrainian.irl mklink %path_x64r%languages\ukrainian.irl %path_trans_l%ukrainian.irl if not exist %path_x64r%languages\valencian.irl mklink %path_x64r%languages\valencian.irl %path_trans_l%valencian.irl if not exist %path_x64r%languages\vietnamese.irl mklink %path_x64r%languages\vietnamese.irl %path_trans_l%vietnamese.irl if not exist %path_x64p%languages\albanian.irl mklink %path_x64p%languages\albanian.irl %path_trans_l%albanian.irl if not exist %path_x64p%languages\arabic.irl mklink %path_x64p%languages\arabic.irl %path_trans_l%arabic.irl if not exist %path_x64p%languages\armenian.irl mklink %path_x64p%languages\armenian.irl %path_trans_l%armenian.irl if not exist %path_x64p%languages\basque.irl mklink %path_x64p%languages\basque.irl %path_trans_l%basque.irl if not exist %path_x64p%languages\bosnian.irl mklink %path_x64p%languages\bosnian.irl %path_trans_l%bosnian.irl if not exist %path_x64p%languages\bulgarian.irl mklink %path_x64p%languages\bulgarian.irl %path_trans_l%bulgarian.irl if not exist %path_x64p%languages\catalan.irl mklink %path_x64p%languages\catalan.irl %path_trans_l%catalan.irl if not exist %path_x64p%languages\chinese-simplified.irl mklink %path_x64p%languages\chinese-simplified.irl %path_trans_l%chinese-simplified.irl if not exist %path_x64p%languages\chinese-traditional.irl mklink %path_x64p%languages\chinese-traditional.irl %path_trans_l%chinese-traditional.irl if not exist %path_x64p%languages\chuvash.irl mklink %path_x64p%languages\chuvash.irl %path_trans_l%chuvash.irl if not exist %path_x64p%languages\croatian.irl mklink %path_x64p%languages\croatian.irl %path_trans_l%croatian.irl if not exist %path_x64p%languages\czech.irl mklink %path_x64p%languages\czech.irl %path_trans_l%czech.irl if not exist %path_x64p%languages\danish.irl mklink %path_x64p%languages\danish.irl %path_trans_l%danish.irl if not exist %path_x64p%languages\dutch.irl mklink %path_x64p%languages\dutch.irl %path_trans_l%dutch.irl if not exist %path_x64p%languages\estonian.irl mklink %path_x64p%languages\estonian.irl %path_trans_l%estonian.irl if not exist %path_x64p%languages\farsi.irl mklink %path_x64p%languages\farsi.irl %path_trans_l%farsi.irl if not exist %path_x64p%languages\finnish.irl mklink %path_x64p%languages\finnish.irl %path_trans_l%finnish.irl if not exist %path_x64p%languages\french.irl mklink %path_x64p%languages\french.irl %path_trans_l%french.irl if not exist %path_x64p%languages\galician.irl mklink %path_x64p%languages\galician.irl %path_trans_l%galician.irl if not exist %path_x64p%languages\german.irl mklink %path_x64p%languages\german.irl %path_trans_l%german.irl if not exist %path_x64p%languages\georgian.irl mklink %path_x64p%languages\georgian.irl %path_trans_l%georgian.irl if not exist %path_x64p%languages\greek.irl mklink %path_x64p%languages\greek.irl %path_trans_l%greek.irl if not exist %path_x64p%languages\hebrew.irl mklink %path_x64p%languages\hebrew.irl %path_trans_l%hebrew.irl if not exist %path_x64p%languages\hungarian.irl mklink %path_x64p%languages\hungarian.irl %path_trans_l%hungarian.irl if not exist %path_x64p%languages\indonesian.irl mklink %path_x64p%languages\indonesian.irl %path_trans_l%indonesian.irl if not exist %path_x64p%languages\italian.irl mklink %path_x64p%languages\italian.irl %path_trans_l%italian.irl if not exist %path_x64p%languages\japanese.irl mklink %path_x64p%languages\japanese.irl %path_trans_l%japanese.irl if not exist %path_x64p%languages\korean.irl mklink %path_x64p%languages\korean.irl %path_trans_l%korean.irl if not exist %path_x64p%languages\latvian.irl mklink %path_x64p%languages\latvian.irl %path_trans_l%latvian.irl if not exist %path_x64p%languages\lithuanian.irl mklink %path_x64p%languages\lithuanian.irl %path_trans_l%lithuanian.irl if not exist %path_x64p%languages\macedonian.irl mklink %path_x64p%languages\macedonian.irl %path_trans_l%macedonian.irl if not exist %path_x64p%languages\norwegian.irl mklink %path_x64p%languages\norwegian.irl %path_trans_l%norwegian.irl if not exist %path_x64p%languages\polish.irl mklink %path_x64p%languages\polish.irl %path_trans_l%polish.irl if not exist %path_x64p%languages\portuguese.irl mklink %path_x64p%languages\portuguese.irl %path_trans_l%portuguese.irl if not exist %path_x64p%languages\portuguese-brazilian.irl mklink %path_x64p%languages\portuguese-brazilian.irl %path_trans_l%portuguese-brazilian.irl if not exist %path_x64p%languages\romanian.irl mklink %path_x64p%languages\romanian.irl %path_trans_l%romanian.irl if not exist %path_x64p%languages\russian.irl mklink %path_x64p%languages\russian.irl %path_trans_l%russian.irl if not exist %path_x64p%languages\serbian-cyrillic.irl mklink %path_x64p%languages\serbian-cyrillic.irl %path_trans_l%serbian-cyrillic.irl if not exist %path_x64p%languages\serbian-latin.irl mklink %path_x64p%languages\serbian-latin.irl %path_trans_l%serbian-latin.irl if not exist %path_x64p%languages\slovak.irl mklink %path_x64p%languages\slovak.irl %path_trans_l%slovak.irl if not exist %path_x64p%languages\slovenian.irl mklink %path_x64p%languages\slovenian.irl %path_trans_l%slovenian.irl if not exist %path_x64p%languages\spanish.irl mklink %path_x64p%languages\spanish.irl %path_trans_l%spanish.irl if not exist %path_x64p%languages\swedish.irl mklink %path_x64p%languages\swedish.irl %path_trans_l%swedish.irl if not exist %path_x64p%languages\thai.irl mklink %path_x64p%languages\thai.irl %path_trans_l%thai.irl if not exist %path_x64p%languages\turkish.irl mklink %path_x64p%languages\turkish.irl %path_trans_l%turkish.irl if not exist %path_x64p%languages\ukrainian.irl mklink %path_x64p%languages\ukrainian.irl %path_trans_l%ukrainian.irl if not exist %path_x64p%languages\valencian.irl mklink %path_x64p%languages\valencian.irl %path_trans_l%valencian.irl if not exist %path_x64p%languages\vietnamese.irl mklink %path_x64p%languages\vietnamese.irl %path_trans_l%vietnamese.irl rem make symbolic links to translated help. if not exist %path_w32d%languages\czech.chm mklink %path_w32d%languages\czech.chm %path_trans_h%czech.chm if not exist %path_w32d%languages\french.chm mklink %path_w32d%languages\french.chm %path_trans_h%french.chm if not exist %path_w32d%languages\german.chm mklink %path_w32d%languages\german.chm %path_trans_h%german.chm if not exist %path_w32d%languages\russian.chm mklink %path_w32d%languages\russian.chm %path_trans_h%russian.chm if not exist %path_w32d%languages\thai.chm mklink %path_w32d%languages\thai.chm %path_trans_h%thai.chm if not exist %path_w32d%languages\turkish.chm mklink %path_w32d%languages\turkish.chm %path_trans_h%turkish.chm if not exist %path_w32d%languages\ukrainian.chm mklink %path_w32d%languages\ukrainian.chm %path_trans_h%ukrainian.chm if not exist %path_w32r%languages\czech.chm mklink %path_w32r%languages\czech.chm %path_trans_h%czech.chm if not exist %path_w32r%languages\french.chm mklink %path_w32r%languages\french.chm %path_trans_h%french.chm if not exist %path_w32r%languages\german.chm mklink %path_w32r%languages\german.chm %path_trans_h%german.chm if not exist %path_w32r%languages\russian.chm mklink %path_w32r%languages\russian.chm %path_trans_h%russian.chm if not exist %path_w32r%languages\thai.chm mklink %path_w32r%languages\thai.chm %path_trans_h%thai.chm if not exist %path_w32r%languages\turkish.chm mklink %path_w32r%languages\turkish.chm %path_trans_h%turkish.chm if not exist %path_w32r%languages\ukrainian.chm mklink %path_w32r%languages\ukrainian.chm %path_trans_h%ukrainian.chm if not exist %path_w32p%languages\czech.chm mklink %path_w32p%languages\czech.chm %path_trans_h%czech.chm if not exist %path_w32p%languages\french.chm mklink %path_w32p%languages\french.chm %path_trans_h%french.chm if not exist %path_w32p%languages\german.chm mklink %path_w32p%languages\german.chm %path_trans_h%german.chm if not exist %path_w32p%languages\russian.chm mklink %path_w32p%languages\russian.chm %path_trans_h%russian.chm if not exist %path_w32p%languages\thai.chm mklink %path_w32p%languages\thai.chm %path_trans_h%thai.chm if not exist %path_w32p%languages\turkish.chm mklink %path_w32p%languages\turkish.chm %path_trans_h%turkish.chm if not exist %path_w32p%languages\ukrainian.chm mklink %path_w32p%languages\ukrainian.chm %path_trans_h%ukrainian.chm if not exist %path_x64d%languages\czech.chm mklink %path_x64d%languages\czech.chm %path_trans_h%czech.chm if not exist %path_x64d%languages\french.chm mklink %path_x64d%languages\french.chm %path_trans_h%french.chm if not exist %path_x64d%languages\german.chm mklink %path_x64d%languages\german.chm %path_trans_h%german.chm if not exist %path_x64d%languages\russian.chm mklink %path_x64d%languages\russian.chm %path_trans_h%russian.chm if not exist %path_x64d%languages\thai.chm mklink %path_x64d%languages\thai.chm %path_trans_h%thai.chm if not exist %path_x64d%languages\turkish.chm mklink %path_x64d%languages\turkish.chm %path_trans_h%turkish.chm if not exist %path_x64d%languages\ukrainian.chm mklink %path_x64d%languages\ukrainian.chm %path_trans_h%ukrainian.chm if not exist %path_x64r%languages\czech.chm mklink %path_x64r%languages\czech.chm %path_trans_h%czech.chm if not exist %path_x64r%languages\french.chm mklink %path_x64r%languages\french.chm %path_trans_h%french.chm if not exist %path_x64r%languages\german.chm mklink %path_x64r%languages\german.chm %path_trans_h%german.chm if not exist %path_x64r%languages\russian.chm mklink %path_x64r%languages\russian.chm %path_trans_h%russian.chm if not exist %path_x64r%languages\thai.chm mklink %path_x64r%languages\thai.chm %path_trans_h%thai.chm if not exist %path_x64r%languages\turkish.chm mklink %path_x64r%languages\turkish.chm %path_trans_h%turkish.chm if not exist %path_x64r%languages\ukrainian.chm mklink %path_x64r%languages\ukrainian.chm %path_trans_h%ukrainian.chm if not exist %path_x64p%languages\czech.chm mklink %path_x64p%languages\czech.chm %path_trans_h%czech.chm if not exist %path_x64p%languages\french.chm mklink %path_x64p%languages\french.chm %path_trans_h%french.chm if not exist %path_x64p%languages\german.chm mklink %path_x64p%languages\german.chm %path_trans_h%german.chm if not exist %path_x64p%languages\russian.chm mklink %path_x64p%languages\russian.chm %path_trans_h%russian.chm if not exist %path_x64p%languages\thai.chm mklink %path_x64p%languages\thai.chm %path_trans_h%thai.chm if not exist %path_x64p%languages\turkish.chm mklink %path_x64p%languages\turkish.chm %path_trans_h%turkish.chm if not exist %path_x64p%languages\ukrainian.chm mklink %path_x64p%languages\ukrainian.chm %path_trans_h%ukrainian.chm pause ================================================ FILE: readme.txt ================================================ InfraRecorder Copyright (C) 2006-2012 Christian Kindahl, christian dot kindahl at gmail dot com This program is licensed under GPL (version 3), please see the file License.txt. Please note that the graphics used in InfraRecorder is not covered by GPL, read the details further down in this document. The InfraRecorder source code can be obtained from http://infrarecorder.org In order to compile InfraRecorder you will need the following libraries: 1. WTL: http://wtl.sourceforge.net 2. ckCore, ckFileSystem and ckMMC: http://code.kindahl.com 3. libpng: http://www.libpng.org InfraRecorder uses cdrtools, sources can be found at: http://cdrecord.berlios.de/ InfraRecorder has been developed with Visual C++ 2005 Professional edition. It is however possible to compile the sources with the free "Express" edition, but you will need to separately obtain and install the ATL library headers. The Microsoft Windows Server 2003 R2 Platform SDK (also free) was the last Windows SDK version to ship with the ATL headers. The bundled ATL 3.0 is rather old, but it is still supported by the latest WTL library. The graphics used in InfraRecorder are NOT covered by GPL. The official InfraRecorder logo (the logo used in official InfraRecorder binaries), and all other graphics using it are licensed under the Creative Commons Attribution-Noncommercial-No Derivative Works license (http://creativecommons.org/licenses/by-nc-nd/3.0/) with one additional condition: * The work may not be used in derivative software or in the purpose of promoting derivative software. Apart from the graphics using the official InfraRecorder logo the above license also applies to all graphics that are not derivative works of graphics created by the Tango Desktop Project. Examples of this kind of graphics are the button graphics used in the welcome screen. The remaining graphics that are derivative work based on icons in the Tango Desktop Project (http://tango.freedesktop.org) is available under the same license as the Tango Desktop Project graphics. That is the Creative Commons Attribution Share-Alike license (http://creativecommons.org/licenses/by-sa/2.5/). ================================================ FILE: sign.bat ================================================ @echo off set cert_file= %~dp0christian_kindahl.pfx set /p cert_pass= < %~dp0christian_kindahl.psw set cert_sats= "http://timestamp.comodoca.com/authenticode" set path_w32r=%~dp0bin\win32\release\ set path_w32p=%~dp0bin\win32\releasep\ set path_x64r=%~dp0bin\x64\release\ set path_x64p=%~dp0bin\x64\releasep\ rem set path_dist=%~dp0dist\ set path_smoke_w32=%~dp0dep\smoke\win32\ set path_smoke_x64=%~dp0dep\smoke\x64\ set path_cdrtools=%~dp0dep\cdrtools\ set path_sndfile_w32=%~dp0dep\libsndfile\win32\ set path_sndfile_x64=%~dp0dep\libsndfile\x64\ if "%~1" NEQ "" goto single_file signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_smoke_w32%smoke.exe signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_smoke_x64%smoke.exe signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_sndfile_w32%libsndfile-1.dll signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_sndfile_x64%libsndfile-1.dll signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_cdrtools%cdda2wav.exe signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_cdrtools%cdrecord.exe signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_cdrtools%readcd.exe signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_cdrtools%cygwin1.dll signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32r%infrarecorder.exe signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32r%shell.dll signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32r%codecs\lame.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32r%codecs\sndfile.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32r%codecs\wave.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32r%codecs\wma.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32r%codecs\vorbis.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32p%infrarecorder.exe signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32p%codecs\lame.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32p%codecs\sndfile.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32p%codecs\wave.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32p%codecs\wma.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_w32p%codecs\vorbis.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64r%infrarecorder.exe signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64r%shell.dll signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64r%codecs\lame.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64r%codecs\sndfile.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64r%codecs\wave.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64r%codecs\wma.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64r%codecs\vorbis.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64p%infrarecorder.exe signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64p%codecs\lame.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64p%codecs\sndfile.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64p%codecs\wave.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64p%codecs\wma.irc signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_x64p%codecs\vorbis.irc rem signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_dist%ir.exe rem signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %path_dist%ir_x64.msi goto end :single_file signtool sign /f %cert_file% /p %cert_pass% /t %cert_sats% %1 goto end :end pause ================================================ FILE: src/app/action_manager.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "settings.hh" #include "core.hh" #include "core2.hh" #include "core2_info.hh" #include "infrarecorder.hh" #include "burn_image_dlg.hh" #include "copy_disc_dlg.hh" #include "copy_image_dlg.hh" #include "info_dlg.hh" #include "tracks_dlg.hh" #include "erase_dlg.hh" #include "fixate_dlg.hh" #include "progress_dlg.hh" #include "simple_progress_dlg.hh" #include "string_table.hh" #include "lang_util.hh" #include "project_manager.hh" #include "scsi.hh" #include "log_dlg.hh" #include "action_manager.hh" CActionManager g_ActionManager; CActionManager::CActionManager() { } CActionManager::~CActionManager() { } static void RemoveTempTracks ( std::vector & TempTracks ) { for ( std::vector ::iterator it = TempTracks.begin(); it != TempTracks.end(); ++it ) { const TCHAR * const elem = *it; ckcore::File::remove(elem); delete [] elem; } TempTracks.clear(); } DWORD WINAPI CActionManager::BurnCompilationThread(LPVOID lpThreadParameter) { struct CLocalData { // The destructor frees these variables automatically. ckcore::File ImageFile; ckfilesystem::FileSet Files; // Files to burn. std::vector TempTracks; const TCHAR *pAudioText; CLocalData(void) : ImageFile(g_BurnImageSettings.m_bOnFly ? ckcore::Path() // 'ImageFile' variable not used. : ckcore::File::temp(g_GlobalSettings.m_szTempPath, ckT("InfraRecorder"))), Files(g_ProjectSettings.m_iFileSystem == FILESYSTEM_DVDVIDEO), pAudioText(NULL) {} ~CLocalData(void) { if (!g_BurnImageSettings.m_bOnFly) ImageFile.remove(); ckfilesystem::destroy_file_set(Files); RemoveTempTracks(TempTracks); // Remove the CD-Text file. if (pAudioText != NULL) ckcore::File::remove(pAudioText); } } LocalData; int iProjectType = g_ProjectManager.GetProjectType(); eBurnResult result = BURNRESULT_INTERNALERROR; // Make sure that the disc will not be ejected before beeing verified. bool bEject = g_BurnImageSettings.m_bEject; g_BurnImageSettings.m_bEject = false; // Used for locating the files on the disc when verifying. std::map FilePathMap; switch (iProjectType) { case PROJECTTYPE_DATA: g_TreeManager.GetPathList(LocalData.Files,g_TreeManager.GetRootNode()); break; case PROJECTTYPE_MIXED: g_TreeManager.GetPathList(LocalData.Files,g_ProjectManager.GetMixDataRootNode(), lstrlen(g_ProjectManager.GetMixDataRootNode()->pItemData->GetFileName()) + 1); break; case PROJECTTYPE_AUDIO: // Audio discs do not have files to burn. break; default: ATLASSERT(false); return 0; }; if (iProjectType == PROJECTTYPE_DATA || iProjectType == PROJECTTYPE_MIXED) { // Set the status information. g_pProgressDlg->SetWindowText(lngGetString(STITLE_PREPOPERATION)); g_pProgressDlg->SetDevice(_T("")); g_pProgressDlg->set_status(lngGetString(STATUS_GATHER_FILE_INFO)); // Create a temporary disc image if not burning on the fly. if (!g_BurnImageSettings.m_bOnFly) { // Set the status information. g_pProgressDlg->SetWindowText(lngGetString(STITLE_CREATEIMAGE)); g_pProgressDlg->SetDevice(lngGetString(PROGRESS_IMAGEDEVICE)); g_pProgressDlg->set_status(lngGetString(STATUS_WRITEIMAGE)); g_pProgressDlg->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINDISCIMAGE)); const int iCreateImageResult = g_Core2.CreateImage(LocalData.ImageFile.name().c_str(),LocalData.Files,*g_pProgressDlg, true,g_BurnImageSettings.m_bVerify ? &FilePathMap : NULL); g_pProgressDlg->set_progress(100); switch (iCreateImageResult) { case RESULT_OK: g_pProgressDlg->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_CREATEIMAGE)); result = BURNRESULT_OK; break; case RESULT_CANCEL: g_pProgressDlg->NotifyCompleted(); return 0; case RESULT_FAIL: g_pProgressDlg->set_status(lngGetString(PROGRESS_FAILED)); g_pProgressDlg->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_CREATEIMAGE)); g_pProgressDlg->NotifyCompleted(); return 0; default: ATLASSERT( false ); }; } } g_pProgressDlg->set_progress(0); ckmmc::Device &Device = *g_BurnImageSettings.m_pRecorder; // Set the status information. g_pProgressDlg->SetWindowText(lngGetString(STITLE_BURNCOMPILATION)); g_pProgressDlg->SetDevice(Device); std::vector AudioTracks; // Decode any encoded tracks in audio and mixed-mode projects. g_pProgressDlg->set_status(lngGetString(PROGRESS_DECODETRACKS)); switch (iProjectType) { case PROJECTTYPE_MIXED: case PROJECTTYPE_AUDIO: g_ProjectManager.GetAudioTracks(AudioTracks); // Decode any audio tracks that might be encoded. if (!g_ProjectManager.DecodeAudioTracks(AudioTracks,LocalData.TempTracks,g_pProgressDlg)) { g_pProgressDlg->NotifyCompleted(); return 0; } break; case PROJECTTYPE_DATA: // No audio tracks to decode. break; default: ATLASSERT( false ); } // Start the burn process. for (long i = 0; i < g_BurnImageSettings.m_lNumCopies; i++) { bool bLast = i == (g_BurnImageSettings.m_lNumCopies - 1); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); switch (iProjectType) { case PROJECTTYPE_DATA: if (g_BurnImageSettings.m_bOnFly) { // Try to estimate the file system size before burning the compilation. unsigned __int64 uiDataSize = 0; g_pProgressDlg->set_status(lngGetString(PROGRESS_ESTIMAGESIZE)); const int iEstimateImageSizeRes = g_Core2.EstimateImageSize(LocalData.Files,*g_pProgressDlg,uiDataSize); g_pProgressDlg->set_progress(100); switch ( iEstimateImageSizeRes ) { case RESULT_OK: // Reset the status. g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); if (g_BurnImageSettings.m_bVerify || !bLast) { result = g_Core.BurnCompilationEx(Device,g_pProgressDlg,*g_pProgressDlg,LocalData.Files, AudioTracks,NULL,g_ProjectSettings.m_iIsoFormat,uiDataSize); } else { const bool bBurnCompilationRes = g_Core.BurnCompilation(Device,g_pProgressDlg,*g_pProgressDlg,LocalData.Files, AudioTracks,NULL,g_ProjectSettings.m_iIsoFormat,uiDataSize); result = bBurnCompilationRes ? BURNRESULT_OK : BURNRESULT_INTERNALERROR; } break; default: ATLASSERT( false ); // Fall through case RESULT_CANCEL: case RESULT_FAIL: g_pProgressDlg->notify(ckcore::Progress::ckERROR,lngGetString(ERROR_ESTIMAGESIZE)); result = BURNRESULT_INTERNALERROR; break; } } else { if (g_BurnImageSettings.m_bVerify || !bLast) { result = g_Core.BurnTracksEx(Device,g_pProgressDlg,LocalData.ImageFile.name().c_str(), AudioTracks,NULL,g_ProjectSettings.m_iIsoFormat); } else { bool bBurnTracksRes = g_Core.BurnTracks(Device,g_pProgressDlg,LocalData.ImageFile.name().c_str(), AudioTracks,NULL,g_ProjectSettings.m_iIsoFormat); result = bBurnTracksRes ? BURNRESULT_OK : BURNRESULT_INTERNALERROR; } } break; case PROJECTTYPE_MIXED: // Save CD-Text information. if (AudioTracks.size() > 0) { // Check if any audio information has been edited. if (g_TreeManager.HasExtraAudioData(g_ProjectManager.GetMixAudioRootNode())) { ckcore::File AudioTextFile = ckcore::File::temp(g_GlobalSettings.m_szTempPath, ckT("InfraRecorder")); if (g_ProjectManager.SaveCDText(AudioTextFile.name().c_str())) LocalData.pAudioText = AudioTextFile.name().c_str(); else lngMessageBox(HWND_DESKTOP,FAILURE_CREATECDTEXT,GENERAL_ERROR,MB_OK | MB_ICONERROR); } } if (g_BurnImageSettings.m_bOnFly) { // Try to estimate the file system size before burning the compilation. unsigned __int64 uiDataSize = 0; g_pProgressDlg->set_status(lngGetString(PROGRESS_ESTIMAGESIZE)); const int iEstimateImageSizeRes = g_Core2.EstimateImageSize(LocalData.Files,*g_pProgressDlg,uiDataSize); g_pProgressDlg->set_progress(100); switch ( iEstimateImageSizeRes ) { case RESULT_OK: // Reset the status. g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); if (g_BurnImageSettings.m_bVerify || !bLast) { result = g_Core.BurnCompilationEx(Device,g_pProgressDlg,*g_pProgressDlg,LocalData.Files, AudioTracks,LocalData.pAudioText,g_ProjectSettings.m_iIsoFormat,uiDataSize); } else { bool bBurnCompilationRes = g_Core.BurnCompilation(Device,g_pProgressDlg,*g_pProgressDlg,LocalData.Files, AudioTracks,LocalData.pAudioText,g_ProjectSettings.m_iIsoFormat,uiDataSize); result = bBurnCompilationRes ? BURNRESULT_OK : BURNRESULT_INTERNALERROR; } break; default: ATLASSERT( false ); // Fall through. case RESULT_CANCEL: case RESULT_FAIL: g_pProgressDlg->notify(ckcore::Progress::ckERROR,lngGetString(ERROR_ESTIMAGESIZE)); result = BURNRESULT_INTERNALERROR; break; } } else { if (g_BurnImageSettings.m_bVerify || !bLast) { result = g_Core.BurnTracksEx(Device,g_pProgressDlg,LocalData.ImageFile.name().c_str(), AudioTracks,LocalData.pAudioText,g_ProjectSettings.m_iIsoFormat); } else { bool bBurnTracksRes = g_Core.BurnTracks(Device,g_pProgressDlg,LocalData.ImageFile.name().c_str(), AudioTracks,LocalData.pAudioText,g_ProjectSettings.m_iIsoFormat); result = bBurnTracksRes ? BURNRESULT_OK : BURNRESULT_INTERNALERROR; } } break; case PROJECTTYPE_AUDIO: // Save CD-Text information. if (AudioTracks.size() > 0) { // Check if any audio information has been edited. if (g_TreeManager.HasExtraAudioData(g_TreeManager.GetRootNode())) { ckcore::File AudioTextFile = ckcore::File::temp(g_GlobalSettings.m_szTempPath, ckT("InfraRecorder")); if (g_ProjectManager.SaveCDText(AudioTextFile.name().c_str())) LocalData.pAudioText = AudioTextFile.name().c_str(); else lngMessageBox(HWND_DESKTOP,FAILURE_CREATECDTEXT,GENERAL_ERROR,MB_OK | MB_ICONERROR); } } if (bLast) { bool bBurnTracksRes = g_Core.BurnTracks(Device,g_pProgressDlg,NULL, AudioTracks,LocalData.pAudioText,0); result = bBurnTracksRes ? BURNRESULT_OK : BURNRESULT_INTERNALERROR; } else { result = g_Core.BurnTracksEx(Device,g_pProgressDlg,NULL, AudioTracks,LocalData.pAudioText,0); } break; default: ATLASSERT( false ); }; // Handle the result. switch ( result ) { default: ATLASSERT( false ); // Fall through case BURNRESULT_INTERNALERROR: case BURNRESULT_EXTERNALERROR: g_pProgressDlg->set_status(lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->NotifyCompleted(); lngMessageBox(HWND_DESKTOP,FAILURE_CDRTOOLS,GENERAL_ERROR,MB_OK | MB_ICONERROR); return 0; case BURNRESULT_OK: break; } // The recording was successful. Verify the disc if requested. if (g_BurnImageSettings.m_bVerify) { // We need to reload the drive media. g_pProgressDlg->set_status(lngGetString(PROGRESS_RELOADMEDIA)); g_Core2.StartStopUnit(Device,CCore2::LOADMEDIA_EJECT,false); if (!g_Core2.StartStopUnit(Device,CCore2::LOADMEDIA_LOAD,false)) lngMessageBox(*g_pProgressDlg,INFO_RELOAD,GENERAL_INFORMATION,MB_OK | MB_ICONINFORMATION); // Set the device information. g_pProgressDlg->SetDevice(Device); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); g_pProgressDlg->SetWindowText(lngGetString(STITLE_VERIFYDISC)); // Get the device drive letter. TCHAR szDriveLetter[3]; szDriveLetter[0] = Device.address().device_[0]; szDriveLetter[1] = ':'; szDriveLetter[2] = '\0'; // Validate the project files. g_ProjectManager.VerifyCompilation(g_pProgressDlg,szDriveLetter,FilePathMap); // We're done. g_pProgressDlg->set_progress(100); g_pProgressDlg->set_status(lngGetString(PROGRESS_DONE)); g_pProgressDlg->NotifyCompleted(); } // Eject the disc if requested. if (bEject) g_Core.EjectDisc(Device,false); if (!bLast) { g_pProgressDlg->set_progress(0); if (!g_pProgressDlg->RequestNextDisc()) { g_pProgressDlg->NotifyCompleted(); break; } TCHAR szBuffer[128]; lsprintf(szBuffer,lngGetString(INFO_CREATECOPY), i + 2, g_BurnImageSettings.m_lNumCopies); g_pProgressDlg->notify(ckcore::Progress::ckINFORMATION,szBuffer); } } return 0; } DWORD WINAPI CActionManager::CreateImageThread(LPVOID lpThreadParameter) { TCHAR *szFileName = (TCHAR *)lpThreadParameter; ckfilesystem::FileSet Files(g_ProjectSettings.m_iFileSystem == FILESYSTEM_DVDVIDEO); try { switch (g_ProjectManager.GetProjectType()) { case PROJECTTYPE_DATA: g_TreeManager.GetPathList(Files,g_TreeManager.GetRootNode()); break; case PROJECTTYPE_MIXED: g_TreeManager.GetPathList(Files,g_ProjectManager.GetMixDataRootNode(), lstrlen(g_ProjectManager.GetMixDataRootNode()->pItemData->GetFileName()) + 1); break; default: ATLASSERT( false ); delete [] szFileName; ckfilesystem::destroy_file_set(Files); return 0; }; // Set the status information. g_pProgressDlg->SetWindowText(lngGetString(STITLE_CREATEIMAGE)); g_pProgressDlg->SetDevice(lngGetString(PROGRESS_IMAGEDEVICE)); g_pProgressDlg->set_status(lngGetString(STATUS_WRITEIMAGE)); g_pProgressDlg->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINDISCIMAGE)); int iResult = g_Core2.CreateImage(szFileName,Files,*g_pProgressDlg,true); g_pProgressDlg->set_progress(100); g_pProgressDlg->NotifyCompleted(); switch (iResult) { case RESULT_OK: g_pProgressDlg->set_status(lngGetString(PROGRESS_DONE)); g_pProgressDlg->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_CREATEIMAGE)); break; case RESULT_FAIL: g_pProgressDlg->set_status(lngGetString(PROGRESS_FAILED)); g_pProgressDlg->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_CREATEIMAGE)); ckcore::File::remove(szFileName); break; case RESULT_CANCEL: ckcore::File::remove(szFileName); break; default: ATLASSERT( false ); } } catch ( ... ) { delete [] szFileName; ckfilesystem::destroy_file_set(Files); throw; } delete [] szFileName; ckfilesystem::destroy_file_set(Files); return 0; } /** Tries to erase the disc inserted in the specified recorder using a fast method. The function will not let you know if it fails. */ void CActionManager::QuickErase(ckmmc::Device &Device) { // Get current profile. ckmmc::Device::Profile Profile = Device.profile(); int iMode = g_EraseSettings.m_iMode; bool bForce = g_EraseSettings.m_bForce; bool bEject = g_EraseSettings.m_bEject; bool bSimulate = g_EraseSettings.m_bSimulate; switch (Profile) { case ckmmc::Device::ckPROFILE_DVDPLUSRW: case ckmmc::Device::ckPROFILE_DVDPLUSRW_DL: g_EraseSettings.m_iMode = CCore2::ERASE_FORMAT_QUICK; break; case ckmmc::Device::ckPROFILE_DVDRAM: g_EraseSettings.m_iMode = CCore2::ERASE_FORMAT_FULL; break; //case ckmmc::Device::ckPROFILE_CDRW: //case ckmmc::Device::ckPROFILE_DVDMINUSRW_RESTOV: //case ckmmc::Device::ckPROFILE_DVDMINUSRW_SEQ: default: g_EraseSettings.m_iMode = CCore2::ERASE_BLANK_MINIMAL; break; } g_EraseSettings.m_iMode = CCore2::ERASE_BLANK_MINIMAL; g_EraseSettings.m_bForce = true; g_EraseSettings.m_bEject = false; g_EraseSettings.m_bSimulate = false; g_EraseSettings.m_pRecorder = &Device; g_EraseSettings.m_uiSpeed = 0xFFFFFFFF; // Maximum. g_pProgressDlg->SetWindowText(lngGetString(STITLE_ERASE)); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); // Set the device information. g_pProgressDlg->SetDevice(Device); // Create the new erase thread. unsigned long ulThreadID = 0; HANDLE hThread = ::CreateThread(NULL,0,EraseThread,new CEraseParam(false),0,&ulThreadID); // Wait for the thread to finish. while (true) { if (WaitForSingleObject(hThread,100) == WAIT_TIMEOUT) { ProcessMessages(); Sleep(100); } else { break; } } ::CloseHandle(hThread); g_pProgressDlg->Reset(); g_pProgressDlg->AllowCancel(true); // Restore settings. g_EraseSettings.m_iMode = iMode; g_EraseSettings.m_bForce = bForce; g_EraseSettings.m_bEject = bEject; g_EraseSettings.m_bSimulate = bSimulate; } /** Depending on the media inserted into the disc this function will try to determine if the media should be erased. This includes asking the user if necessary. */ bool CActionManager::QuickEraseQuery(ckmmc::Device &Device,HWND hWndParent) { if (!g_ProjectSettings.m_bMultiSession) { CCore2Info Info; CCore2DiscInfo DiscInfo; if (Info.ReadDiscInformation(Device,&DiscInfo)) { if (DiscInfo.m_ucDiscStatus != CCore2DiscInfo::DS_EMTPY && DiscInfo.m_ucFlags & CCore2DiscInfo::FLAG_ERASABLE) { if (lngMessageBox(hWndParent,MISC_ERASENONEMPTY,GENERAL_QUESTION, MB_YESNO | MB_ICONQUESTION) == IDYES) { return true; } } } } return false; } INT_PTR CActionManager::BurnCompilation(HWND hWndParent,bool bAppMode) { bool bAudioProject = g_ProjectManager.GetProjectType() == PROJECTTYPE_AUDIO; // Display the burn image dialog. CBurnImageDlg BurnImageDlg(lngGetString(MISC_BURNCOMPILATION),false, !bAudioProject,!bAudioProject,bAppMode); INT_PTR iResult = BurnImageDlg.DoModal(); if (iResult == IDOK) { // Check if we should erase the disc. bool bErase = QuickEraseQuery(*g_BurnImageSettings.m_pRecorder,hWndParent); // Disable the parent window. if (hWndParent != NULL) ::EnableWindow(hWndParent,false); // If we're in application mode we need to create a message loop since // the progress window must run independently. CMessageLoop MainLoop; if (bAppMode) _Module.AddMessageLoop(&MainLoop); // Create and display the progress dialog. g_pProgressDlg->SetAppMode(bAppMode); if (!g_pProgressDlg->IsWindow()) g_pProgressDlg->Create(hWndParent); g_pProgressDlg->ShowWindow(true); g_pProgressDlg->Reset(); g_pProgressDlg->AttachProcess(&g_Core); g_pProgressDlg->AttachHost(hWndParent); ProcessMessages(); if (bErase) QuickErase(*g_BurnImageSettings.m_pRecorder); // Create the new thread. unsigned long ulThreadID = 0; HANDLE hThread = ::CreateThread(NULL,0,BurnCompilationThread,this,0,&ulThreadID); ::CloseHandle(hThread); // Run the message loop if we're in application mode. if (bAppMode) { iResult = MainLoop.Run(); _Module.RemoveMessageLoop(); return iResult; } } return iResult; } INT_PTR CActionManager::CreateImage(HWND hWndParent,bool bAppMode) { WTL::CFileDialog FileDialog(false,_T("iso"),_T("Untitled"),OFN_EXPLORER | OFN_OVERWRITEPROMPT, _T("Disc Images (*.iso)\0*.iso\0\0"),hWndParent); INT_PTR iResult = FileDialog.DoModal(); if (iResult == IDOK) { // Disable the parent window. if (hWndParent != NULL) ::EnableWindow(hWndParent,false); // If we're in application mode we need to create a message loop since // the progress window must run independently. CMessageLoop MainLoop; if (bAppMode) _Module.AddMessageLoop(&MainLoop); // Create and display the progress dialog. g_pProgressDlg->SetAppMode(bAppMode); if (!g_pProgressDlg->IsWindow()) g_pProgressDlg->Create(hWndParent); g_pProgressDlg->ShowWindow(true); g_pProgressDlg->Reset(); g_pProgressDlg->AttachProcess(&g_Core); g_pProgressDlg->AttachHost(hWndParent); ProcessMessages(); // WARNING: Heap allocation, this memory memory must be freed when the thread exit. TCHAR *szFileName = new TCHAR[MAX_PATH]; lstrcpy(szFileName,FileDialog.m_szFileName); // Create the new thread. unsigned long ulThreadID = 0; HANDLE hThread = ::CreateThread(NULL,0,CreateImageThread,szFileName,0,&ulThreadID); ::CloseHandle(hThread); // Run the message loop if we're in application mode. if (bAppMode) { iResult = MainLoop.Run(); _Module.RemoveMessageLoop(); return iResult; } } return iResult; } INT_PTR CActionManager::BurnImage(HWND hWndParent,bool bAppMode) { WTL::CFileDialog FileDialog(true,0,0,OFN_FILEMUSTEXIST | OFN_EXPLORER, _T("Disc Images (*.iso, *.cue, *.img)\0*.iso;*.cue;*.img\0Raw Images (*.bin, *.raw)\0*.bin;*.raw\0All Files (*.*)\0*.*\0\0"),hWndParent); INT_PTR iResult = FileDialog.DoModal(); if (iResult == IDOK) iResult = BurnImageEx(hWndParent,bAppMode,FileDialog.m_szFileName); return iResult; } INT_PTR CActionManager::BurnImageEx(HWND hWndParent,bool bAppMode,const TCHAR *szFilePath) { // Dialog title. TCHAR szFileName[MAX_PATH]; lstrcpy(szFileName,szFilePath); ExtractFileName(szFileName); TCHAR szTitle[MAX_PATH]; lstrcpy(szTitle,lngGetString(MISC_BURN)); lstrcat(szTitle,szFileName); // Look for a TOC file. TCHAR szTOCFilePath[MAX_PATH]; lstrcpy(szTOCFilePath,szFilePath); lstrcat(szTOCFilePath,_T(".toc")); bool bImageHasTOC = false; if (ckcore::File::exist(szTOCFilePath)) bImageHasTOC = true; // Display the burn image dialog. CBurnImageDlg BurnImageDlg(szTitle,bImageHasTOC,false,false,bAppMode); INT_PTR iResult = BurnImageDlg.DoModal(); if (iResult == IDOK) { // Check if we should erase the disc. bool bErase = QuickEraseQuery(*g_BurnImageSettings.m_pRecorder,hWndParent); ckmmc::Device &Device = *g_BurnImageSettings.m_pRecorder; // Disable the parent window. if (hWndParent != NULL) ::EnableWindow(hWndParent,false); // If we're in application mode we need to create a message loop since // the progress window must run independently. CMessageLoop MainLoop; if (bAppMode) _Module.AddMessageLoop(&MainLoop); // Create and display the progress dialog. g_pProgressDlg->SetAppMode(bAppMode); if (!g_pProgressDlg->IsWindow()) g_pProgressDlg->Create(hWndParent); g_pProgressDlg->ShowWindow(true); //g_pProgressDlg->SetWindowText(lngGetString(STITLE_BURNIMAGE)); g_pProgressDlg->Reset(); g_pProgressDlg->AttachProcess(&g_Core); g_pProgressDlg->AttachHost(hWndParent); ProcessMessages(); // Erase the disc if necessary. if (bErase) QuickErase(Device); // Set the device information. g_pProgressDlg->SetWindowText(lngGetString(STITLE_BURNIMAGE)); g_pProgressDlg->SetDevice(Device); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); // Begin burning the image. if (!g_Core.BurnImage(Device,g_pProgressDlg,szFilePath,bImageHasTOC)) { g_pProgressDlg->set_status(lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->NotifyCompleted(); lngMessageBox(HWND_DESKTOP,FAILURE_CDRTOOLS,GENERAL_ERROR,MB_OK | MB_ICONERROR); } // Run the message loop if we're in application mode. if (bAppMode) { iResult = MainLoop.Run(); _Module.RemoveMessageLoop(); return iResult; } } return iResult; } DWORD WINAPI CActionManager::CopyDiscOnFlyThread(LPVOID lpThreadParameter) { // Get device information. ckmmc::Device &SrcDevice = *g_CopyDiscSettings.m_pSource; ckmmc::Device &DstDevice = *g_CopyDiscSettings.m_pTarget; // Set the status information. g_pProgressDlg->SetWindowText(lngGetString(STITLE_COPYDISC)); g_pProgressDlg->SetDevice(DstDevice); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); // Start the operation. if (!g_Core.CopyDisc(SrcDevice,DstDevice,g_pProgressDlg)) { g_pProgressDlg->set_status(lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->NotifyCompleted(); lngMessageBox(HWND_DESKTOP,FAILURE_CDRTOOLS,GENERAL_ERROR,MB_OK | MB_ICONERROR); return 0; } return 0; } DWORD WINAPI CActionManager::CopyDiscThread(LPVOID lpThreadParameter) { ckcore::File ImageFile = ckcore::File::temp(g_GlobalSettings.m_szTempPath, ckT("InfraRecorder")); // Set the status information. g_pProgressDlg->SetWindowText(lngGetString(STITLE_CREATEIMAGE)); g_pProgressDlg->SetDevice(lngGetString(PROGRESS_IMAGEDEVICE)); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); // Get device information. ckmmc::Device &SrcDevice = *g_CopyDiscSettings.m_pSource; // Override the read sub-channel data setting. g_ReadSettings.m_bClone = g_CopyDiscSettings.m_bClone; eBurnResult iResult = g_Core.ReadDiscEx(SrcDevice,g_pProgressDlg,ImageFile.name().c_str()); switch (iResult) { default: ATLASSERT( false ); // Fall through case BURNRESULT_INTERNALERROR: g_pProgressDlg->set_status(lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->NotifyCompleted(); lngMessageBox(HWND_DESKTOP,FAILURE_CDRTOOLS,GENERAL_ERROR,MB_OK | MB_ICONERROR); // Remove any temporary files. ImageFile.remove(); if (g_CopyDiscSettings.m_bClone) { ckcore::tstring TocName = ImageFile.name(); TocName += ckT(".toc"); ckcore::File::remove(TocName.c_str()); } return 0; case BURNRESULT_EXTERNALERROR: // Remove any temporary files. ImageFile.remove(); if (g_CopyDiscSettings.m_bClone) { ckcore::tstring TocName = ImageFile.name(); TocName += ckT(".toc"); ckcore::File::remove(TocName.c_str()); } return 0; case BURNRESULT_OK: break; } // Ask the user to switch discs if the target is the same as the source. if (g_CopyDiscSettings.m_pSource == g_CopyDiscSettings.m_pTarget) { g_Core2.StartStopUnit(SrcDevice,CCore2::LOADMEDIA_EJECT,true); if (lngMessageBox(*g_pProgressDlg,INFO_INSERTBLANK,GENERAL_INFORMATION, MB_OKCANCEL | MB_ICONINFORMATION) == IDCANCEL) { g_pProgressDlg->set_status(lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->NotifyCompleted(); // Remove any temporary files. ImageFile.remove(); if (g_CopyDiscSettings.m_bClone) { ckcore::tstring TocName = ImageFile.name(); TocName += ckT(".toc"); ckcore::File::remove(TocName.c_str()); } return 0; } } // Get device information. ckmmc::Device &DstDevice = *g_CopyDiscSettings.m_pTarget; // Set the status information. g_pProgressDlg->SetWindowText(lngGetString(STITLE_BURNIMAGE)); g_pProgressDlg->SetDevice(DstDevice); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); if (!g_Core.BurnImageEx(DstDevice,g_pProgressDlg,ImageFile.name().c_str(), g_CopyDiscSettings.m_bClone)) { g_pProgressDlg->set_status(lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->NotifyCompleted(); lngMessageBox(HWND_DESKTOP,FAILURE_CDRTOOLS,GENERAL_ERROR,MB_OK | MB_ICONERROR); } // Remove any temporary files. ImageFile.remove(); if (g_CopyDiscSettings.m_bClone) { ckcore::tstring TocName = ImageFile.name(); TocName += ckT(".toc"); ckcore::File::remove(TocName.c_str()); } return 0; } DWORD WINAPI CActionManager::EraseThread(LPVOID lpThreadParameter) { std::auto_ptr Param((CEraseParam *)lpThreadParameter); // Get device information. ckmmc::Device &Device = *g_EraseSettings.m_pRecorder; bool bResult = g_Core2.EraseDisc(Device,g_pProgressDlg,g_EraseSettings.m_iMode, g_EraseSettings.m_bForce,g_EraseSettings.m_bEject,g_EraseSettings.m_bSimulate, g_EraseSettings.m_uiSpeed); g_pProgressDlg->set_progress(100); if (Param->m_bNotifyCompleted) g_pProgressDlg->NotifyCompleted(); if (bResult) { g_pProgressDlg->set_status(lngGetString(PROGRESS_DONE)); } else { g_pProgressDlg->set_status(lngGetString(PROGRESS_FAILED)); g_pProgressDlg->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_ERASE)); } return true; } INT_PTR CActionManager::CopyDisc(HWND hWndParent,bool bAppMode) { // Display the information dialog. if (g_GlobalSettings.m_bCopyWarning) { CInfoDlg InfoDlg(&g_GlobalSettings.m_bCopyWarning,lngGetString(INFO_COPYDISC)); if (InfoDlg.DoModal() == IDCANCEL) return IDCANCEL; } // Display the burn image dialog. CCopyDiscDlg CopyDiscDlg(bAppMode); INT_PTR iResult = CopyDiscDlg.DoModal(); if (iResult == IDOK) { if (g_CopyDiscSettings.m_pSource == g_CopyDiscSettings.m_pTarget) { ckmmc::Device &Device = *g_CopyDiscSettings.m_pSource; g_Core2.StartStopUnit(Device,CCore2::LOADMEDIA_EJECT,true); if (lngMessageBox(hWndParent,INFO_INSERTSOURCE,GENERAL_INFORMATION, MB_OKCANCEL | MB_ICONINFORMATION) == IDCANCEL) { return IDCANCEL; } } // Disable the parent window. if (hWndParent != NULL) ::EnableWindow(hWndParent,false); // If we're in application mode we need to create a message loop since // the progress window must run independently. CMessageLoop MainLoop; if (bAppMode) _Module.AddMessageLoop(&MainLoop); // Create and display the progress dialog. g_pProgressDlg->SetAppMode(bAppMode); if (!g_pProgressDlg->IsWindow()) g_pProgressDlg->Create(hWndParent); g_pProgressDlg->ShowWindow(true); g_pProgressDlg->Reset(); g_pProgressDlg->AttachProcess(&g_Core); g_pProgressDlg->AttachHost(hWndParent); ProcessMessages(); // Create the new thread. unsigned long ulThreadID = 0; HANDLE hThread = ::CreateThread(NULL,0,g_CopyDiscSettings.m_bOnFly ? CopyDiscOnFlyThread : CopyDiscThread,NULL,0,&ulThreadID); ::CloseHandle(hThread); // Run the message loop if we're in application mode. if (bAppMode) { iResult = MainLoop.Run(); _Module.RemoveMessageLoop(); return iResult; } } return iResult; } /* CActionManager::CopyImage ------------------------- Performs the copy disc to a disc image action. */ INT_PTR CActionManager::CopyImage(HWND hWndParent,bool bAppMode) { // Display the copy image dialog. CCopyImageDlg CopyImageDlg(bAppMode); INT_PTR iResult = CopyImageDlg.DoModal(); if (iResult == IDOK) { ckmmc::Device &Device = *g_CopyDiscSettings.m_pSource; // Disable the parent window. if (hWndParent != NULL) ::EnableWindow(hWndParent,false); // If we're in application mode we need to create a message loop since // the progress window must run independently. CMessageLoop MainLoop; if (bAppMode) _Module.AddMessageLoop(&MainLoop); // Create and display the progress dialog. g_pProgressDlg->SetAppMode(bAppMode); if (!g_pProgressDlg->IsWindow()) g_pProgressDlg->Create(hWndParent); g_pProgressDlg->ShowWindow(true); g_pProgressDlg->SetWindowText(lngGetString(STITLE_CREATEIMAGE)); g_pProgressDlg->Reset(); g_pProgressDlg->AttachProcess(&g_Core); g_pProgressDlg->AttachHost(hWndParent); ProcessMessages(); // Set the device information. g_pProgressDlg->SetDevice(Device); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); // Begin reading the disc. if (!g_Core.ReadDisc(Device,g_pProgressDlg,CopyImageDlg.GetFileName())) { g_pProgressDlg->set_status(lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); g_pProgressDlg->NotifyCompleted(); lngMessageBox(HWND_DESKTOP,FAILURE_CDRTOOLS,GENERAL_ERROR,MB_OK | MB_ICONERROR); } // Run the message loop if we're in application mode. if (bAppMode) { iResult = MainLoop.Run(); _Module.RemoveMessageLoop(); return iResult; } } return iResult; } INT_PTR CActionManager::ManageTracks(bool bAppMode) { CTracksDlg TracksDlg(bAppMode); return TracksDlg.DoModal(); } INT_PTR CActionManager::Erase(HWND hWndParent,bool bAppMode) { CEraseDlg EraseDlg(bAppMode); INT_PTR iResult = EraseDlg.DoModal(); if (iResult == IDOK) { ckmmc::Device &Device = *g_EraseSettings.m_pRecorder; // Disable the parent window. if (hWndParent != NULL) ::EnableWindow(hWndParent,false); // If we're in application mode we need to create a message loop since // the progress window must run independently. CMessageLoop MainLoop; if (bAppMode) _Module.AddMessageLoop(&MainLoop); // Create and display the progress dialog. g_pProgressDlg->SetAppMode(bAppMode); if (!g_pProgressDlg->IsWindow()) g_pProgressDlg->Create(hWndParent); g_pProgressDlg->ShowWindow(true); g_pProgressDlg->SetWindowText(lngGetString(STITLE_ERASE)); g_pProgressDlg->Reset(); g_pProgressDlg->AttachProcess(&g_Core); g_pProgressDlg->AttachHost(hWndParent); ProcessMessages(); // Set the device information. g_pProgressDlg->SetDevice(Device); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); // Create the new thread. unsigned long ulThreadID = 0; HANDLE hThread = ::CreateThread(NULL,0,EraseThread,new CEraseParam(true),0,&ulThreadID); // Run the message loop if we're in application mode. if (bAppMode) { iResult = MainLoop.Run(); _Module.RemoveMessageLoop(); return iResult; } ::CloseHandle(hThread); } return iResult; } INT_PTR CActionManager::Fixate(HWND hWndParent,bool bAppMode) { CFixateDlg FixateDlg(bAppMode); INT_PTR iResult = FixateDlg.DoModal(); if (iResult == IDOK) { ckmmc::Device &Device = *g_FixateSettings.m_pRecorder; // Disable the parent window. if (hWndParent != NULL) ::EnableWindow(hWndParent,false); // If we're in application mode we need to create a message loop since // the progress window must run independently. CMessageLoop MainLoop; if (bAppMode) _Module.AddMessageLoop(&MainLoop); // Create and display the progress dialog. g_pSimpleProgressDlg->SetAppMode(bAppMode); if (!g_pSimpleProgressDlg->IsWindow()) g_pSimpleProgressDlg->Create(hWndParent); g_pSimpleProgressDlg->ShowWindow(true); g_pSimpleProgressDlg->SetWindowText(lngGetString(STITLE_FIXATE)); g_pSimpleProgressDlg->Reset(); g_pSimpleProgressDlg->AttachProcess(&g_Core); g_pSimpleProgressDlg->AttachHost(hWndParent); ProcessMessages(); // Set the device information. g_pSimpleProgressDlg->SetDevice(Device); g_pSimpleProgressDlg->set_status(lngGetString(PROGRESS_INIT)); // Begin erasing the disc. if (!g_Core.FixateDisc(Device,g_pSimpleProgressDlg, g_FixateSettings.m_bEject, g_FixateSettings.m_bSimulate)) { g_pSimpleProgressDlg->set_status(lngGetString(PROGRESS_CANCELED)); g_pSimpleProgressDlg->notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); g_pSimpleProgressDlg->NotifyCompleted(); lngMessageBox(HWND_DESKTOP,FAILURE_CDRTOOLS,GENERAL_ERROR,MB_OK | MB_ICONERROR); } // Run the message loop if we're in application mode. if (bAppMode) { iResult = MainLoop.Run(); _Module.RemoveMessageLoop(); return iResult; } } return iResult; } // For testing purposes only. /*int CActionManager::VerifyCompilation(HWND hWndParent) { tDeviceInfo *pDeviceInfo = g_DeviceManager.GetDeviceInfo(g_BurnImageSettings.m_iRecorder); tDeviceCap *pDeviceCap = g_DeviceManager.GetDeviceCap(g_BurnImageSettings.m_iRecorder); tDeviceInfoEx *pDeviceInfoEx = g_DeviceManager.GetDeviceInfoEx(g_BurnImageSettings.m_iRecorder); // Disable the parent window. if (hWndParent != NULL) ::EnableWindow(hWndParent,false); // Create and display the progress dialog. g_pProgressDlg->SetAppMode(false); if (!g_pProgressDlg->IsWindow()) g_pProgressDlg->Create(hWndParent); g_pProgressDlg->ShowWindow(true); g_pProgressDlg->SetWindowText(lngGetString(STITLE_BURNIMAGE)); g_pProgressDlg->Reset(); g_pProgressDlg->AttachProcess(&g_Core); g_pProgressDlg->AttachHost(hWndParent); ProcessMessages(); // Set the device information. TCHAR szDeviceName[128]; g_DeviceManager.GetDeviceName(pDeviceInfo,szDeviceName); g_pProgressDlg->SetDevice(szDeviceName); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); // Get the device drive letter. TCHAR szDriveLetter[3]; szDriveLetter[1] = ':'; szDriveLetter[2] = '\0'; bool bFoundDriveLetter = true; if (!SCSIGetDriveLetter(2,1,0,szDriveLetter[0])) { // This is not water proof. External USB and FireWire devices will fail the above // function call because USB and FireWire devices can't return an address on the // requested form since the USB and FireWire bus can contain multiple devices. // In a second attempt to locate the drive a search is performed by the device name. // If two identical devices are connected (same revision) to the system there will // be a conflict. Maybe I should solve this by using the ASPI driver? if (!SCSIGetDriveLetter(pDeviceInfo->szVendor,pDeviceInfo->szIdentification, pDeviceInfo->szRevision,szDriveLetter[0])) { bFoundDriveLetter = false; } } if (bFoundDriveLetter) { // Validate the project files. g_ProjectManager.VerifyCompilation(g_pProgressDlg,szDriveLetter); } else { // Add to progress dialog instead? MessageBox(hWndParent,_T("InfraRecorder was unable to determine the drive letter of your recorder. The disc can not be verified."),lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); } // We're done. g_pProgressDlg->set_progress(100); g_pProgressDlg->set_status(lngGetString(PROGRESS_DONE)); g_pProgressDlg->NotifyCompleted(); return 0; }*/ ================================================ FILE: src/app/action_manager.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CActionManager { private: class CEraseParam { public: bool m_bNotifyCompleted; CEraseParam(bool bNotifyCompleted) : m_bNotifyCompleted(bNotifyCompleted) {} }; static DWORD WINAPI BurnCompilationThread(LPVOID lpThreadParameter); static DWORD WINAPI CreateImageThread(LPVOID lpThreadParameter); static DWORD WINAPI CopyDiscOnFlyThread(LPVOID lpThreadParameter); static DWORD WINAPI CopyDiscThread(LPVOID lpThreadParameter); static DWORD WINAPI EraseThread(LPVOID lpThreadParameter); void QuickErase(ckmmc::Device &Device); bool QuickEraseQuery(ckmmc::Device &Device,HWND hWndParent); public: CActionManager(); ~CActionManager(); INT_PTR BurnCompilation(HWND hWndParent,bool bAppMode); INT_PTR CreateImage(HWND hWndParent,bool bAppMode); INT_PTR BurnImage(HWND hWndParent,bool bAppMode); INT_PTR BurnImageEx(HWND hWndParent,bool bAppMode,const TCHAR *szFilePath); INT_PTR CopyDisc(HWND hWndParent,bool bAppMode); INT_PTR CopyImage(HWND hWndParent,bool bAppMode); INT_PTR ManageTracks(bool bAppMode); INT_PTR Erase(HWND hWndParent,bool bAppMode); INT_PTR Fixate(HWND hWndParent,bool bAppMode); // For testing purposes only. //int VerifyCompilation(HWND hWndParent); }; extern CActionManager g_ActionManager; ================================================ FILE: src/app/advanced_progress.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "advanced_progress.hh" void CAdvancedProgress::SetBuffer(int iPercent) { // Do nothing. } ================================================ FILE: src/app/advanced_progress.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #define PROGRESS_STRINGBUFFER_SIZE 256 class CAdvancedProgress : public ckcore::Progress { protected: // Should be used by inheritors when parsing the variable argument list passed // to the AddLogEntry and SetStatus functions. TCHAR m_szStringBuffer[PROGRESS_STRINGBUFFER_SIZE]; public: // Called when the operation is complteted. virtual void NotifyCompleted() = 0; // Should be set to true when a real writing process is started. virtual void SetRealMode(bool bRealMode) = 0; // Not forced to be implemented by inheritor. virtual void SetBuffer(int iPercent); virtual void AllowReload() = 0; virtual void AllowCancel(bool bAllow) = 0; virtual bool RequestNextDisc() = 0; // Starts the smoke effect. virtual void StartSmoke() = 0; }; ================================================ FILE: src/app/atl_compat.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once inline ATL::CWindow GetParentWindow(const ATL::CWindow *pWnd) { // Version 3.0 of the ATL library does not have the CWindow::GetParent() // overload that returns a CWindow object. Unfortunately, ATL 3.0 is the // latest freely available version of the ATL library, it comes with the // Microsoft Windows Server 2003 R2 Platform SDK. Supporting ATL 3.0 means // you can compile InfraRecorder with Visual Studio 2005 Express, which is // also free. WTL 8.0 also supports ATL 3.0 / Visual Studio 2005 Express, // see the bundled readme file. // // The missing GetParent() overload is actually very handy, and this routine // is a good workaround that works on both ATL 3.0 and the newer versions. // // An alternative to this routine would be to manually add the missing // overload to the ATL 3.0 headers. This is however cumbersome for the casual // developer who just wants to compile the project once. Modifying the // standard headers may also cause compilation trouble in other projects or // with other versions of Visual Studio. #if _ATL_VER <= 0x0300 return ATL::CWindow(pWnd->GetParent()); #else // Use the one that comes with ATL. return pWnd->GetParent(); #endif } #if _ATL_VER <= 0x0300 #pragma comment(lib,"shell32") #pragma comment(lib,"gdi32") #pragma comment(lib,"comdlg32") #endif ================================================ FILE: src/app/control/custom_button.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "resource.h" #include "custom_button.hh" CCustomButton::CCustomButton(unsigned short usCoverPng,int iCoverLeft,int iCoverRight) : m_State(STATE_NORMAL),m_iCoverLeft(iCoverLeft),m_iCoverTop(iCoverRight) { // Load the images. m_CoverImage.Open(usCoverPng); m_NormalImage.Open(IDR_BUTTONNPNG); m_FocusImage.Open(IDR_BUTTONFPNG); m_HoverImage.Open(IDR_BUTTONHPNG); m_HoverFocusImage.Open(IDR_BUTTONHFPNG); } CCustomButton::~CCustomButton() { } LRESULT CCustomButton::OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { TRACKMOUSEEVENT tme = { 0 }; tme.cbSize = sizeof(TRACKMOUSEEVENT); tme.hwndTrack = m_hWnd; tme.dwFlags = TME_LEAVE; tme.dwHoverTime = 10000; bool bMouseHover = TrackMouseEvent(&tme) == TRUE; if (bMouseHover && m_State == STATE_NORMAL) { m_State = STATE_HOT; RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); } return 0; } LRESULT CCustomButton::OnMouseLeave(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_State = STATE_NORMAL; RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); return 0; } LRESULT CCustomButton::OnLButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (m_State == STATE_HOT) { m_State = STATE_DOWN; RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); } return 0; } LRESULT CCustomButton::OnLButtonUp(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (m_State == STATE_DOWN) { m_State = STATE_HOT; RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); } return 0; } LRESULT CCustomButton::OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { return 0; } void CCustomButton::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct) { CDCHandle dc = lpDrawItemStruct->hDC; RECT rcClient; GetClientRect(&rcClient); FillRect(dc,&rcClient,GetSysColorBrush(COLOR_WINDOW)); switch (m_State) { case STATE_NORMAL: if (lpDrawItemStruct->itemState & ODS_FOCUS) m_FocusImage.Draw(dc,0,0,rcClient.right,rcClient.bottom); else m_NormalImage.Draw(dc,0,0,rcClient.right,rcClient.bottom); break; case STATE_HOT: case STATE_DOWN: if (lpDrawItemStruct->itemState & ODS_FOCUS) m_HoverFocusImage.Draw(dc,0,0,rcClient.right,rcClient.bottom); else m_HoverImage.Draw(dc,0,0,rcClient.right,rcClient.bottom); break; } m_CoverImage.Draw(dc,m_iCoverLeft,m_iCoverTop,rcClient.right,rcClient.bottom); ReleaseDC(dc); } ================================================ FILE: src/app/control/custom_button.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "png_file.hh" class CCustomButton : public CWindowImpl, public COwnerDraw { private: enum eState { STATE_NORMAL, STATE_HOT, STATE_DOWN }; eState m_State; int m_iCoverLeft; int m_iCoverTop; CPngFile m_CoverImage; CPngFile m_NormalImage; CPngFile m_FocusImage; CPngFile m_HoverImage; CPngFile m_HoverFocusImage; public: DECLARE_WND_CLASS(_T("ckButton")); CCustomButton(unsigned short usCoverPng,int iCoverLeft,int iCoverRight); ~CCustomButton(); BEGIN_MSG_MAP(CCustomButton) MESSAGE_HANDLER(WM_MOUSEMOVE,OnMouseMove) MESSAGE_HANDLER(WM_MOUSELEAVE,OnMouseLeave) //MESSAGE_HANDLER(WM_LBUTTONDOWN,OnLButtonDown) //MESSAGE_HANDLER(WM_LBUTTONUP,OnLButtonUp) MESSAGE_HANDLER(WM_ERASEBKGND,OnEraseBkgnd) CHAIN_MSG_MAP_ALT(COwnerDraw,1) END_MSG_MAP() LRESULT OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnMouseLeave(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnLButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnLButtonUp(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); // For ownerdraw. void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct); }; ================================================ FILE: src/app/control/custom_combo_box.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "custom_combo_box.hh" /* A custom combo box control that provides item icons to the left of the text. The data property determines the icon index of an combo box item. To get proper dimensions: m_TrackCombo.SetItemHeight( 0,16); m_TrackCombo.SetItemHeight(-1,16); // Static item. */ CCustomComboBox::CCustomComboBox() : m_hImageList(NULL),m_iImageList(0) { } CCustomComboBox::~CCustomComboBox() { } void CCustomComboBox::SetImageList(HIMAGELIST hImageList,int iImageList) { m_hImageList = hImageList; m_iImageList = iImageList; } void CCustomComboBox::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct) { CDCHandle dc = lpDrawItemStruct->hDC; RECT rcItem = lpDrawItemStruct->rcItem; bool bSelected = (lpDrawItemStruct->itemState & ODS_SELECTED) != 0; bool bFocused = (lpDrawItemStruct->itemState & ODS_FOCUS) != 0; bool bDisabled = (lpDrawItemStruct->itemState & ODS_DISABLED) != 0; int iBackgroundColor; if (bDisabled) iBackgroundColor = COLOR_BTNFACE; else if (bSelected) iBackgroundColor = COLOR_HIGHLIGHT; else iBackgroundColor = COLOR_WINDOW; // Draw the background. HBRUSH hBackground = ::GetSysColorBrush(iBackgroundColor); dc.FillRect(&rcItem,hBackground); // Draw icon. if (!bDisabled && m_hImageList != NULL) { ImageList_Draw(m_hImageList,(int)lpDrawItemStruct->itemData,dc, rcItem.left, rcItem.top,ILD_TRANSPARENT); rcItem.left += 16 + CUSTOMCOMBO_ICONSPACING; } // Draw the text. HFONT hOldFont = (HFONT)dc.SelectFont(AtlGetDefaultGuiFont()); int iTextColor; if (bDisabled) iTextColor = COLOR_GRAYTEXT; else if (bSelected) iTextColor = COLOR_HIGHLIGHTTEXT; else iTextColor = COLOR_WINDOWTEXT; dc.SetBkMode(TRANSPARENT); dc.SetTextColor(::GetSysColor(iTextColor)); TCHAR szText[128]; if (GetLBTextLen(lpDrawItemStruct->itemID) >= (sizeof(szText) / sizeof(TCHAR) - 1)) { TCHAR *szVarText = new TCHAR[GetLBTextLen(lpDrawItemStruct->itemID) + 1]; GetLBText(lpDrawItemStruct->itemID,szVarText); dc.DrawText(szVarText,lstrlen(szVarText),&rcItem,DT_LEFT | DT_VCENTER | DT_END_ELLIPSIS | DT_SINGLELINE); delete [] szVarText; } else { GetLBText(lpDrawItemStruct->itemID,szText); dc.DrawText(szText,lstrlen(szText),&rcItem,DT_LEFT | DT_VCENTER | DT_END_ELLIPSIS | DT_SINGLELINE); } if (bFocused) dc.DrawFocusRect(&rcItem); dc.SelectFont(hOldFont); } ================================================ FILE: src/app/control/custom_combo_box.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #define CUSTOMCOMBO_ICONSPACING 1 class CCustomComboBox : public CWindowImpl, public COwnerDraw { private: HIMAGELIST m_hImageList; int m_iImageList; public: DECLARE_WND_CLASS(_T("ckComboBox")); CCustomComboBox(); ~CCustomComboBox(); BEGIN_MSG_MAP(CCustomComboBox) CHAIN_MSG_MAP_ALT(COwnerDraw,1) END_MSG_MAP() LRESULT OnChar(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); void SetImageList(HIMAGELIST hImageList,int iImageList); // For ownerdraw. void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct); }; ================================================ FILE: src/app/control/custom_container.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "custom_container.hh" #include "settings.hh" #include "ctrl_messages.hh" #include "main_frm.hh" CCustomContainer::CCustomContainer() { m_iHeaderHeight = 0; m_hWndCustomDraw = NULL; m_iControlID = -1; } CCustomContainer::~CCustomContainer() { } void CCustomContainer::SetCustomDrawHandler(HWND hWndCustomDraw,int iID) { m_hWndCustomDraw = hWndCustomDraw; m_iControlID = iID; } void CCustomContainer::SetClient(HWND hWndClient) { m_ClientWindow = hWndClient; UpdateLayout(); } void CCustomContainer::SetImageList(HIMAGELIST hImageList) { m_ToolBar.SetImageList(hImageList); //m_ToolBar.SetButtonStructSize(); } void CCustomContainer::UpdateLayout() { RECT rcClient; GetClientRect(&rcClient); UpdateLayout(rcClient.right,rcClient.bottom); } void CCustomContainer::UpdateLayout(int iWidth,int iHeight) { RECT rcHeader = { 0,0,iWidth,m_iHeaderHeight }; if (m_ClientWindow.m_hWnd != NULL) m_ClientWindow.SetWindowPos(NULL,0,m_iHeaderHeight,iWidth,iHeight - m_iHeaderHeight,SWP_NOZORDER); else rcHeader.bottom = iHeight; InvalidateRect(&rcHeader); } void CCustomContainer::AddToolBarSeparator() { TBBUTTON tbButton; tbButton.fsState = TBSTATE_ENABLED; tbButton.fsStyle = TBSTYLE_SEP; tbButton.iBitmap = 0; tbButton.idCommand = 0; tbButton.iString = 0; tbButton.dwData = 0; m_ToolBar.InsertButton(m_ToolBar.GetButtonCount(),&tbButton); } void CCustomContainer::AddToolBarButton(int iCommand,int iBitmap) { TBBUTTON tbButton; tbButton.fsState = TBSTATE_ENABLED; tbButton.fsStyle = TBSTYLE_BUTTON; tbButton.iBitmap = iBitmap; tbButton.idCommand = iCommand; tbButton.iString = NULL; tbButton.dwData = 0; m_ToolBar.InsertButton(m_ToolBar.GetButtonCount(),&tbButton); } void CCustomContainer::UpdateToolBar() { // Update the toolbar position. int iToolBarWidth = 0; RECT rcButton; for (int i = 0; i < m_ToolBar.GetButtonCount(); i++) { m_ToolBar.GetItemRect(i,&rcButton); iToolBarWidth += rcButton.right - rcButton.left; } m_iHeaderHeight = HIWORD(m_ToolBar.GetButtonSize()); m_ToolBar.SetWindowPos(NULL,0,0,iToolBarWidth,m_iHeaderHeight,0); } void CCustomContainer::EnableToolbarButton(int iID,bool bEnable) { m_ToolBar.EnableButton(iID,bEnable); } LRESULT CCustomContainer::OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { RECT rcToolBar = { 0,0,100,100 }; m_ToolBar.Create(m_hWnd,rcToolBar,NULL,ATL_SIMPLE_TOOLBAR_PANE_STYLE,NULL); m_ToolBar.SetButtonStructSize(); return 0; } LRESULT CCustomContainer::OnSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { UpdateLayout(GET_X_LPARAM(lParam),GET_Y_LPARAM(lParam)); return 0; } LRESULT CCustomContainer::OnSetFocus(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (m_ClientWindow.m_hWnd != NULL) m_ClientWindow.SetFocus(); return 0; } LRESULT CCustomContainer::OnCommand(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Redirect messages to the parent. if (m_ToolBar.m_hWnd != NULL && (HWND)lParam == m_ToolBar.m_hWnd) return ::SendMessage(GetParent(),WM_COMMAND,wParam,(LPARAM)m_hWnd); bHandled = false; return TRUE; } LRESULT CCustomContainer::OnGetIShellBrowser(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // This is very important, we need to redirect this message to the main frame that can return // the correct IShellBrowser object. If we do not answer to this message the CreateViewObject // function call will fail on Windows 98 systems for all other directories than the desktop. bHandled = TRUE; return ::SendMessage(*g_pMainFrame,WM_GETISHELLBROWSER,wParam,lParam); } LRESULT CCustomContainer::OnCustomDraw(int idCtrl,LPNMHDR pnmh,BOOL &bHandled) { if (m_hWndCustomDraw != NULL && idCtrl == m_iControlID) return ::SendMessage(m_hWndCustomDraw,WM_CONTROLCUSTOMDRAW,0,(LPARAM)pnmh); bHandled = false; return CDRF_DODEFAULT; } LRESULT CCustomContainer::OnToolBarGetInfo(int idCtrl,LPNMHDR pNMH,BOOL &bHandled) { bHandled = true; // The string ID is the same as the button ID. LPTOOLTIPTEXT pTipText = (LPTOOLTIPTEXT)pNMH; //pTipText->lpszText = MAKEINTRESOURCE(pTipText->hdr.idFrom); // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a hint translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("hint"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr((unsigned long)pTipText->hdr.idFrom,szStrValue)) { pTipText->lpszText = szStrValue; return 0; } } } // I am not sure if I want the tool tips to be displayed on the toolbar. // This method is also to slow. /*TCHAR szBuffer[256]; LoadString(_Module.GetResourceInstance(),pTipText->hdr.idFrom,szBuffer,sizeof(szBuffer) / sizeof(TCHAR)); m_StatusBar.SetPaneText(ID_DEFAULT_PANE,szBuffer);*/ pTipText->lpszText = MAKEINTRESOURCE(pTipText->hdr.idFrom); return 0; } int CCustomContainer::GetHeaderHeight() { return m_iHeaderHeight; } ================================================ FILE: src/app/control/custom_container.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #ifndef WM_GETISHELLBROWSER #define WM_GETISHELLBROWSER WM_USER + 7 #endif class CCustomContainer : public CWindowImpl { private: CToolBarCtrl m_ToolBar; CWindow m_ClientWindow; int m_iHeaderHeight; // Handle to the control that should receivce custom draw messages. HWND m_hWndCustomDraw; int m_iControlID; public: static CWndClassInfo &GetWndClassInfo() { static CWndClassInfo wc = { { sizeof(WNDCLASSEX),CS_DBLCLKS, StartWindowProc,0,0,NULL,NULL,NULL, GetSysColorBrush(COLOR_BTNFACE),NULL, _T("ckCustomContainer"),NULL }, NULL,NULL,IDC_ARROW,TRUE,0,_T("") }; return wc; } CCustomContainer(); ~CCustomContainer(); void SetCustomDrawHandler(HWND hWndCustomDraw,int iID); BEGIN_MSG_MAP(CCustomContainer) MESSAGE_HANDLER(WM_CREATE,OnCreate) MESSAGE_HANDLER(WM_SIZE,OnSize) MESSAGE_HANDLER(WM_SETFOCUS,OnSetFocus) MESSAGE_HANDLER(WM_COMMAND,OnCommand) MESSAGE_HANDLER(WM_GETISHELLBROWSER,OnGetIShellBrowser) NOTIFY_CODE_HANDLER(NM_CUSTOMDRAW,OnCustomDraw) NOTIFY_CODE_HANDLER(TTN_GETDISPINFO,OnToolBarGetInfo) FORWARD_NOTIFICATIONS() END_MSG_MAP() LRESULT OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSetFocus(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnCommand(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnCustomDraw(int idCtrl,LPNMHDR pnmh,BOOL &bHandled); LRESULT OnGetIShellBrowser(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnToolBarGetInfo(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); void SetClient(HWND hWndClient); void SetImageList(HIMAGELIST hImageList); void UpdateLayout(); void UpdateLayout(int iWidth,int iHeight); void AddToolBarSeparator(); void AddToolBarButton(int iCommand,int iBitmap); void UpdateToolBar(); void EnableToolbarButton(int iID,bool bEnable); int GetHeaderHeight(); }; ================================================ FILE: src/app/control/custom_edit_ctrl.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "custom_edit_ctrl.hh" CCustomEditCtrl::CCustomEditCtrl() { } CCustomEditCtrl::~CCustomEditCtrl() { } /* CCustomEditCtrl::OnChar ----------------------- This edit control works like a regular edit control except that it does not allow the | (pipe) character. */ LRESULT CCustomEditCtrl::OnChar(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { bHandled = wParam == '|'; return 0; } ================================================ FILE: src/app/control/custom_edit_ctrl.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CCustomEditCtrl : public CWindowImpl { public: CCustomEditCtrl(); ~CCustomEditCtrl(); BEGIN_MSG_MAP(CCustomEditCtrl) MESSAGE_HANDLER(WM_CHAR,OnChar) END_MSG_MAP() LRESULT OnChar(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/control/custom_header_ctrl.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "custom_header_ctrl.hh" #include "project_manager.hh" #include "tree_manager.hh" CCustomHeaderCtrl::CCustomHeaderCtrl() { m_bSortUp = true; m_iSortCol = 0; } void CCustomHeaderCtrl::SetSortColumn(unsigned int uiColIndex,bool bSortUp) { m_bSortUp = bSortUp; m_iSortCol = uiColIndex; HDITEM hdColumn; hdColumn.mask = HDI_FORMAT; GetItem(m_iSortCol,&hdColumn); if (m_bSortUp) { hdColumn.fmt |= HDF_SORTUP; hdColumn.fmt &= ~HDF_SORTDOWN; } else { hdColumn.fmt |= HDF_SORTDOWN; hdColumn.fmt &= ~HDF_SORTUP; } SetItem(m_iSortCol,&hdColumn); } LRESULT CCustomHeaderCtrl::OnSetSortColumn(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { SetSortColumn((unsigned int)wParam,lParam == 0); return 0; } void CCustomHeaderCtrl::ColumnClick(unsigned int uiColIndex) { if (m_iSortCol == uiColIndex) { // Set the new sort arrow. SetSortColumn(uiColIndex,!m_bSortUp); } else { // Remove the sort arrow from the previous column. HDITEM hdColumn; hdColumn.mask = HDI_FORMAT; GetItem(m_iSortCol,&hdColumn); hdColumn.fmt &= ~(m_bSortUp ? HDF_SORTUP : HDF_SORTDOWN); SetItem(m_iSortCol,&hdColumn); // Set the new sort arrow. SetSortColumn(uiColIndex,true); } // Do the sorting. g_TreeManager.GetCurrentNode()->Sort(uiColIndex,m_bSortUp,g_ProjectManager.GetViewType() != PROJECTVIEWTYPE_DATA); g_TreeManager.Refresh(); } ================================================ FILE: src/app/control/custom_header_ctrl.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "ctrl_messages.hh" #if (_WIN32_WINNT < 0x501) #define HDF_SORTUP 0x0400 #define HDF_SORTDOWN 0x0200 #endif class CCustomHeaderCtrl : public CWindowImpl { private: bool m_bSortUp; unsigned int m_iSortCol; void SetSortColumn(unsigned int uiColIndex,bool bSortUp); public: CCustomHeaderCtrl(); BEGIN_MSG_MAP(CCustomHeaderCtrl) MESSAGE_HANDLER(WM_CHC_SETSORTCOLUMN,OnSetSortColumn) END_MSG_MAP() LRESULT OnSetSortColumn(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); void ColumnClick(unsigned int uiColIndex); }; ================================================ FILE: src/app/control/custom_multi_button.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "resource.h" #include "custom_multi_button.hh" CCustomMultiButton::CCustomMultiButton(long lCtrlMainId,long lCtrlSub1Id,long lCtrlSub2Id, unsigned short usCoverPng,int iCoverLeft,int iCoverRight) : m_lCtrlMainId(lCtrlMainId),m_lCtrlSub1Id(lCtrlSub1Id),m_lCtrlSub2Id(lCtrlSub2Id), m_State(STATE_NORMAL),m_iCoverLeft(iCoverLeft),m_iCoverTop(iCoverRight) { // Load the images. m_CoverImage.Open(usCoverPng); m_NormalImage.Open(IDR_MBUTTONNPNG); m_FocusImage.Open(IDR_MBUTTONFPNG); m_HoverImage.Open(IDR_MBUTTONHPNG); m_HoverSub1Image.Open(IDR_MBUTTONHS1PNG); m_HoverSub2Image.Open(IDR_MBUTTONHS2PNG); m_HoverFocusImage.Open(IDR_MBUTTONFPNG); m_HoverFocusSub1Image.Open(IDR_MBUTTONHFS1PNG); m_HoverFocusSub2Image.Open(IDR_MBUTTONHFS2PNG); } CCustomMultiButton::~CCustomMultiButton() { } LRESULT CCustomMultiButton::OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { TRACKMOUSEEVENT tme = { 0 }; tme.cbSize = sizeof(TRACKMOUSEEVENT); tme.hwndTrack = m_hWnd; tme.dwFlags = TME_LEAVE; tme.dwHoverTime = 10000; TrackMouseEvent(&tme); int iPosX = GET_X_LPARAM(lParam); int iPosY = GET_Y_LPARAM(lParam); eState NewState; if (iPosX < SPLITTER_X) NewState = STATE_HOTMAIN; else if (iPosY < SPLITTER_Y) NewState = STATE_HOTSUB1; else NewState = STATE_HOTSUB2; if (NewState != m_State) { RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); } m_State = NewState; return 0; } LRESULT CCustomMultiButton::OnMouseLeave(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_State = STATE_NORMAL; RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); return 0; } LRESULT CCustomMultiButton::OnLButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (m_State == STATE_HOTMAIN || m_State == STATE_HOTSUB1 || m_State == STATE_HOTSUB2) { m_State = STATE_DOWN; RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); } return 0; } LRESULT CCustomMultiButton::OnLButtonUp(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (m_State == STATE_DOWN) { m_State = STATE_HOTMAIN; RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); } // Take action. int iPosX = GET_X_LPARAM(lParam); int iPosY = GET_Y_LPARAM(lParam); if (iPosX < SPLITTER_X) ::PostMessage(GetParent(),WM_COMMAND,m_lCtrlMainId,0); else if (iPosY < SPLITTER_Y) ::PostMessage(GetParent(),WM_COMMAND,m_lCtrlSub1Id,0); else ::PostMessage(GetParent(),WM_COMMAND,m_lCtrlSub2Id,0); return 0; } LRESULT CCustomMultiButton::OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { return 0; } void CCustomMultiButton::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct) { CDCHandle dc = lpDrawItemStruct->hDC; RECT rcClient; GetClientRect(&rcClient); FillRect(dc,&rcClient,GetSysColorBrush(COLOR_WINDOW)); switch (m_State) { case STATE_NORMAL: if (lpDrawItemStruct->itemState & ODS_FOCUS) m_FocusImage.Draw(dc,0,0,rcClient.right,rcClient.bottom); else m_NormalImage.Draw(dc,0,0,rcClient.right,rcClient.bottom); break; case STATE_HOTMAIN: if (lpDrawItemStruct->itemState & ODS_FOCUS) m_HoverFocusImage.Draw(dc,0,0,rcClient.right,rcClient.bottom); else m_HoverImage.Draw(dc,0,0,rcClient.right,rcClient.bottom); break; case STATE_HOTSUB1: if (lpDrawItemStruct->itemState & ODS_FOCUS) m_HoverFocusSub1Image.Draw(dc,0,0,rcClient.right,rcClient.bottom); else m_HoverSub1Image.Draw(dc,0,0,rcClient.right,rcClient.bottom); break; case STATE_HOTSUB2: if (lpDrawItemStruct->itemState & ODS_FOCUS) m_HoverFocusSub2Image.Draw(dc,0,0,rcClient.right,rcClient.bottom); else m_HoverSub2Image.Draw(dc,0,0,rcClient.right,rcClient.bottom); break; } m_CoverImage.Draw(dc,m_iCoverLeft,m_iCoverTop,rcClient.right,rcClient.bottom); ReleaseDC(dc); } ================================================ FILE: src/app/control/custom_multi_button.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "png_file.hh" class CCustomMultiButton : public CWindowImpl, public COwnerDraw { private: enum eState { STATE_NORMAL, STATE_HOTMAIN, STATE_HOTSUB1, STATE_HOTSUB2, STATE_DOWN }; enum { SPLITTER_X = 99, SPLITTER_Y = 36 }; eState m_State; long m_lCtrlMainId; long m_lCtrlSub1Id; long m_lCtrlSub2Id; int m_iCoverLeft; int m_iCoverTop; CPngFile m_CoverImage; CPngFile m_NormalImage; CPngFile m_FocusImage; CPngFile m_HoverImage; CPngFile m_HoverSub1Image; CPngFile m_HoverSub2Image; CPngFile m_HoverFocusImage; CPngFile m_HoverFocusSub1Image; CPngFile m_HoverFocusSub2Image; public: DECLARE_WND_CLASS(_T("ckMultiButton")); CCustomMultiButton(long lCtrlMainId,long lCtrlSub1Id,long lCtrlSub2Id, unsigned short usCoverPng,int iCoverLeft,int iCoverRight); ~CCustomMultiButton(); BEGIN_MSG_MAP(CCustomMultiButton) MESSAGE_HANDLER(WM_MOUSEMOVE,OnMouseMove) MESSAGE_HANDLER(WM_MOUSELEAVE,OnMouseLeave) MESSAGE_HANDLER(WM_LBUTTONDOWN,OnLButtonDown) MESSAGE_HANDLER(WM_LBUTTONUP,OnLButtonUp) MESSAGE_HANDLER(WM_ERASEBKGND,OnEraseBkgnd) CHAIN_MSG_MAP_ALT(COwnerDraw,1) END_MSG_MAP() LRESULT OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnMouseLeave(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnLButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnLButtonUp(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); // For ownerdraw. void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct); }; ================================================ FILE: src/app/control/custom_toolbar_ctrl.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "custom_toolbar_ctrl.hh" #include "main_frm.hh" CCustomToolBarCtrl::CCustomToolBarCtrl() { } CCustomToolBarCtrl::~CCustomToolBarCtrl() { } LRESULT CCustomToolBarCtrl::OnRButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { POINT ptCursor; GetCursorPos(&ptCursor); HMENU hToolBarsMenu = g_pMainFrame->GetToolBarsMenu(); // Force the popup menu items to update. This is needed since WTL seems to be lazy // and only want to refresh the corresponding main menu items when needed. CMainFrame::_AtlUpdateUIData UIData; UIData.m_lpData = NULL; UIData.m_wState = (WORD)g_pMainFrame->UIGetState(ID_VIEW_STANDARDTOOLBAR); g_pMainFrame->UIUpdateMenuBarElement(ID_VIEW_STANDARDTOOLBAR,&UIData,hToolBarsMenu); // Show the popup menu. TrackPopupMenuEx(hToolBarsMenu,0,ptCursor.x,ptCursor.y,m_hWnd,NULL); bHandled = false; return 0; } LRESULT CCustomToolBarCtrl::OnLButtonDblClk(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // We don't want to display the original customize toolbar dialog when the // toolbar is double-clicked on. bHandled = true; return 0; } ================================================ FILE: src/app/control/custom_toolbar_ctrl.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CCustomToolBarCtrl : public CWindowImpl { public: DECLARE_WND_CLASS(_T("ckToolBar")); CCustomToolBarCtrl(); ~CCustomToolBarCtrl(); BEGIN_MSG_MAP(CCustomToolBarCtrl) MESSAGE_HANDLER(WM_RBUTTONDOWN,OnRButtonDown) MESSAGE_HANDLER(WM_LBUTTONDBLCLK,OnLButtonDblClk) END_MSG_MAP() LRESULT OnRButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnLButtonDblClk(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/control/double_buffered_static.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "double_buffered_static.hh" CDoubleBufferedStatic::CDoubleBufferedStatic() { m_Text.reserve(DOUBLEBUFFEREDSTATIC_RESERVE_LENGTH); } CDoubleBufferedStatic::~CDoubleBufferedStatic() { } void CDoubleBufferedStatic::SetWindowText(const TCHAR *szWindowText) { m_Text = szWindowText; RedrawWindow(); } LRESULT CDoubleBufferedStatic::OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CPaintDC dc(m_hWnd); RECT rcClient; GetClientRect(&rcClient); // Setup double buffering. HDC hMemDC = CreateCompatibleDC(dc); HBITMAP hMemBitmap = CreateCompatibleBitmap(dc,rcClient.right,rcClient.bottom); HBITMAP hOldBitmap = (HBITMAP)SelectObject(hMemDC,hMemBitmap); // Draw the background. FillRect(hMemDC,&rcClient,GetSysColorBrush(COLOR_BTNFACE)); // Draw the text. HFONT hOldFont = (HFONT)SelectObject(hMemDC,AtlGetDefaultGuiFont()); ::SetTextColor(hMemDC,GetSysColor(COLOR_BTNTEXT)); ::SetBkColor(hMemDC,GetSysColor(COLOR_BTNFACE)); DrawText(hMemDC,m_Text.c_str(),(int)m_Text.length(),&rcClient, DT_LEFT | DT_END_ELLIPSIS | DT_SINGLELINE); SelectObject(hMemDC,hOldFont); BitBlt(dc,0,0,rcClient.right,rcClient.bottom,hMemDC,0,0,SRCCOPY); SelectObject(hMemDC,hOldBitmap); DeleteDC(hMemDC); DeleteObject(hMemBitmap); bHandled = true; return 0; } LRESULT CDoubleBufferedStatic::OnEraseBkGnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { bHandled = true; return 0; } ================================================ FILE: src/app/control/double_buffered_static.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #define DOUBLEBUFFEREDSTATIC_RESERVE_LENGTH 256 class CDoubleBufferedStatic : public CWindowImpl { private: tstring m_Text; public: CDoubleBufferedStatic(); ~CDoubleBufferedStatic(); void SetWindowText(const TCHAR *szWindowText); BEGIN_MSG_MAP(CDoubleBufferedStatic) MESSAGE_HANDLER(WM_PAINT,OnPaint) MESSAGE_HANDLER(WM_ERASEBKGND,OnEraseBkGnd) END_MSG_MAP() LRESULT OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnEraseBkGnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/control/drop_down_button.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "drop_down_button.hh" CDropDownButton::CDropDownButton(unsigned int uiMenuID,bool bDrawArrow) { m_bDrawArrow = bDrawArrow; // Menu. m_hMenu = LoadMenu(_Module.GetResourceInstance(),MAKEINTRESOURCE(uiMenuID)); // Font used for the arrow (if unthemed only). CFont apa; CLogFont lf = AtlGetDefaultGuiFont(); lstrcpy(lf.lfFaceName,_T("Webdings")); lf.lfCharSet = SYMBOL_CHARSET; lf.lfHeight = 18; m_hWebdingsFont = CreateFontIndirect(&lf); // Theme data. m_hTheme = NULL; } CDropDownButton::~CDropDownButton() { // Menu. DestroyMenu(m_hMenu); // Arrow font. DeleteObject(m_hWebdingsFont); // Unload theme data. if (m_hTheme != NULL) g_VisualStyles.CloseThemeData(m_hTheme); } HMENU CDropDownButton::GetMenu() { return m_hMenu; } BOOL CDropDownButton::SubclassWindow(HWND hWnd) { BOOL bResult = CWindowImpl::SubclassWindow(hWnd); if (m_bDrawArrow) { SetButtonStyle(g_VisualStyles.IsAppThemed() ? BS_PUSHBUTTON : BS_OWNERDRAW); // Load theme data. if (g_VisualStyles.IsAppThemed()) m_hTheme = g_VisualStyles.OpenThemeData(m_hWnd,L"TOOLBAR"); } return bResult; } void CDropDownButton::DrawItem(LPDRAWITEMSTRUCT lpDIS) { CDCHandle dc = lpDIS->hDC; RECT rcItem = lpDIS->rcItem; bool bEnabled = (lpDIS->itemState & ODS_DISABLED) == 0; bool bFocused = (lpDIS->itemState & ODS_FOCUS) != 0; // Draw the button. RECT rcButton = rcItem; if (bFocused) { dc.Draw3dRect(&rcButton,::GetSysColor(COLOR_3DDKSHADOW),::GetSysColor(COLOR_3DDKSHADOW)); ::InflateRect(&rcButton,-1, -1); } unsigned int uiState = 0; if (lpDIS->itemState & ODS_SELECTED) { uiState |= DFCS_PUSHED; ::OffsetRect(&rcItem,1,1); } if (!bEnabled) uiState |= DFCS_INACTIVE; ::DrawFrameControl(dc,&rcButton,DFC_BUTTON,DFCS_BUTTONPUSH | uiState); // Draw the text. TCHAR szText[DROPDOWNBUTTON_MAX_TEXT_SIZE]; GetWindowText(szText,DROPDOWNBUTTON_MAX_TEXT_SIZE - 1); HFONT hOldFont = dc.SelectFont(GetFont()); dc.SetBkMode(TRANSPARENT); dc.SetTextColor(::GetSysColor(bEnabled ? COLOR_BTNTEXT : COLOR_GRAYTEXT)); if (!bEnabled) { RECT rcText = rcItem; RECT rcBound = rcText; dc.DrawText(szText,-1,&rcBound,DT_SINGLELINE | DT_LEFT | DT_TOP | DT_CALCRECT); ::OffsetRect(&rcText,(rcText.right - rcBound.right) / 2, (rcText.bottom - rcBound.bottom) / 2); ::DrawState(dc,NULL,NULL,(LPARAM)szText,0,rcText.left,rcText.top,rcText.right,rcText.bottom,DST_PREFIXTEXT | DSS_DISABLED); } else { RECT rcText = rcItem; dc.DrawText(szText,-1,&rcText,DT_SINGLELINE | DT_CENTER | DT_VCENTER); } // Draw the separator. RECT rcSeparator = { rcItem.right - 22,rcItem.top + 5,rcItem.right - 20,rcItem.bottom - 5 }; dc.Draw3dRect(&rcSeparator,::GetSysColor(COLOR_BTNSHADOW),::GetSysColor(COLOR_BTNHIGHLIGHT)); dc.SelectFont(m_hWebdingsFont); RECT rcArrow = { rcItem.right - 18,rcItem.top,rcItem.right,rcItem.bottom }; dc.DrawText(_T("\x36"),1,&rcArrow,DT_SINGLELINE | DT_LEFT | DT_VCENTER); HBRUSH hOldBrush = dc.SelectBrush((HBRUSH)::GetStockObject(HOLLOW_BRUSH)); ::InflateRect(&rcButton,-3,-3); // Draw the focus rectangle. if (bFocused) dc.DrawFocusRect(&rcButton); dc.SelectBrush(hOldBrush); dc.SelectFont(hOldFont); } DWORD CDropDownButton::OnPrePaint(int idCtrl,LPNMCUSTOMDRAW lpNMCD) { return CDRF_NOTIFYPOSTPAINT; } DWORD CDropDownButton::OnPostPaint(int idCtrl,LPNMCUSTOMDRAW lpNMCD) { CDCHandle dc = lpNMCD->hdc; RECT rcButton = lpNMCD->rc; bool bEnabled = (lpNMCD->uItemState & (CDIS_DISABLED | CDIS_GRAYED)) == 0; // Draw the separator RECT rcSeparator = { rcButton.right - 21,rcButton.top + 4,rcButton.right - 19,rcButton.bottom - 4 }; g_VisualStyles.DrawThemeBackground(m_hTheme,dc,TP_SEPARATOR,TS_NORMAL,&rcSeparator,NULL); // Draw the arrow. RECT rcArrow = { rcButton.right - 22,rcButton.top,rcButton.right,rcButton.bottom }; g_VisualStyles.DrawThemeBackground(m_hTheme,dc, TP_SPLITBUTTONDROPDOWN,bEnabled ? TS_NORMAL : TS_DISABLED,&rcArrow,NULL); return CDRF_DODEFAULT; } LRESULT CDropDownButton::OnClicked(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { RECT rcButton; GetWindowRect(&rcButton); int iID = TrackPopupMenuEx(GetSubMenu(m_hMenu,0),TPM_NONOTIFY | TPM_RETURNCMD, rcButton.left,rcButton.bottom,m_hWnd,NULL); ::PostMessage(GetParent(),WM_COMMAND,iID,0); bHandled = false; return 0; } ================================================ FILE: src/app/control/drop_down_button.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include // BEGIN_MSG_MAP_EX #include "visual_styles.hh" #define DROPDOWNBUTTON_MAX_TEXT_SIZE 64 class CDropDownButton : public CWindowImpl, public COwnerDraw, public CCustomDraw { private: bool m_bDrawArrow; HMENU m_hMenu; HFONT m_hWebdingsFont; HTHEME m_hTheme; public: CDropDownButton(unsigned int uiMenuID,bool bDrawArrow); ~CDropDownButton(); HMENU GetMenu(); BOOL SubclassWindow(HWND hWnd); void DrawItem(LPDRAWITEMSTRUCT lpDIS); DWORD OnPrePaint(int idCtrl,LPNMCUSTOMDRAW lpNMCD); DWORD OnPostPaint(int idCtrl,LPNMCUSTOMDRAW lpNMCD); #if _ATL_VER <= 0x0300 BEGIN_MSG_MAP_EX(CDropDownButton) #else BEGIN_MSG_MAP(CDropDownButton) #endif REFLECTED_COMMAND_CODE_HANDLER(BN_CLICKED,OnClicked) CHAIN_MSG_MAP_ALT(COwnerDraw,1) CHAIN_MSG_MAP_ALT(CCustomDraw,1) END_MSG_MAP() LRESULT OnClicked(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/control/gradient_static.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "gradient_static.hh" CGradientStatic::CGradientStatic(COLORREF TopColor) : m_TopColor(TopColor) { } CGradientStatic::~CGradientStatic() { } LRESULT CGradientStatic::OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { LRESULT lResult = DefWindowProc(uMsg,wParam,lParam); HDC hDC = GetWindowDC(); RECT rcClient; GetClientRect(&rcClient); DrawVertGradientRect(hDC,&rcClient,m_TopColor,GetSysColor(COLOR_BTNFACE)); ReleaseDC(hDC); return lResult; } ================================================ FILE: src/app/control/gradient_static.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CGradientStatic : public CWindowImpl { private: COLORREF m_TopColor; public: CGradientStatic(COLORREF TopColor); ~CGradientStatic(); BEGIN_MSG_MAP(CGradientStatic) MESSAGE_HANDLER(WM_PAINT,OnPaint) END_MSG_MAP() LRESULT OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/control/label_container.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "label_container.hh" #include #include "ctrl_messages.hh" #include "version.hh" #include "visual_styles.hh" #include "resource.h" #include "ctrl_messages.hh" CLabelContainer::CLabelContainer(bool bClosable) { m_iHeaderHeight = 0; m_hBorderBrush = ::CreateSolidBrush(LABELCONTAINER_COLOR_BORDER); m_szLabelText[0] = '\0'; m_hWndCustomDraw = NULL; m_iControlID = -1; // Button releated. m_hCloseImageList = NULL; m_hWndCloseHost = NULL; if (bClosable) InitializeImageList(); m_iButtonState = PANE_BUTTON_NORMAL; m_bButtonDown = false; } CLabelContainer::~CLabelContainer() { if (m_hBorderBrush != NULL) ::DeleteObject(m_hBorderBrush); // Destroy the image list. if (m_hCloseImageList != NULL) ImageList_Destroy(m_hCloseImageList); } void CLabelContainer::InitializeImageList() { HBITMAP hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_PANECLOSEBITMAP)); m_hCloseImageList = ImageList_Create(16,16,ILC_COLOR32 | ILC_MASK,0,4); ImageList_AddMasked(m_hCloseImageList,hBitmap,RGB(255,0,255)); DeleteObject(hBitmap); } void CLabelContainer::SetCustomDrawHandler(HWND hWndCustomDraw,int iID) { m_hWndCustomDraw = hWndCustomDraw; m_iControlID = iID; } void CLabelContainer::SetClient(HWND hWndClient) { m_ClientWindow = hWndClient; UpdateLayout(); } void CLabelContainer::SetCloseHost(HWND hWndCloseHost) { m_hWndCloseHost = hWndCloseHost; } void CLabelContainer::UpdateLayout() { RECT rcClient; GetClientRect(&rcClient); UpdateLayout(rcClient.right,rcClient.bottom); } void CLabelContainer::UpdateLayout(int iWidth,int iHeight) { RECT rcHeader = { 0,0,iWidth,m_iHeaderHeight }; if (m_ClientWindow.m_hWnd != NULL) m_ClientWindow.SetWindowPos(NULL,0,m_iHeaderHeight,iWidth,iHeight - m_iHeaderHeight,SWP_NOZORDER); else rcHeader.bottom = iHeight; InvalidateRect(&rcHeader); } LRESULT CLabelContainer::OnSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { UpdateLayout(GET_X_LPARAM(lParam),GET_Y_LPARAM(lParam)); return 0; } LRESULT CLabelContainer::OnSetFocus(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (m_ClientWindow.m_hWnd != NULL) m_ClientWindow.SetFocus(); return 0; } LRESULT CLabelContainer::OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { return TRUE; } LRESULT CLabelContainer::OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { RECT rcHeader; GetClientRect(&rcHeader); rcHeader.bottom = rcHeader.top + m_iHeaderHeight; if (wParam != NULL) { HDC hDC = (HDC)wParam; DrawBackground(hDC,&rcHeader); DrawText(hDC,&rcHeader); DrawButton(hDC,&rcHeader); ReleaseDC(hDC); } else { CPaintDC dc(m_hWnd); DrawBackground(dc.m_hDC,&rcHeader); DrawText(dc.m_hDC,&rcHeader); DrawButton(dc.m_hDC,&rcHeader); ReleaseDC(dc); } return 0; } LRESULT CLabelContainer::OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Only deal with this event if the panel is closable. if (m_hCloseImageList == NULL) return 0; POINT ptMouse = { GET_X_LPARAM(lParam),GET_Y_LPARAM(lParam) }; RECT rcButton,rcClient; GetClientRect(&rcClient); rcButton.top = rcClient.top + LABELCONTAINER_BUTTON_TOPSPACING; rcButton.right = rcClient.right - LABELCONTAINER_BUTTON_RIGHTSPACING; rcButton.bottom = rcButton.top + 16; rcButton.left = rcButton.right - 16; int iNewState; if (::PtInRect(&rcButton,ptMouse)) { SetCapture(); if (m_iButtonState != PANE_BUTTON_DOWN) iNewState = PANE_BUTTON_HOVER; else iNewState = PANE_BUTTON_DOWN; } else { ReleaseCapture(); iNewState = PANE_BUTTON_NORMAL; } if (iNewState != m_iButtonState) { m_iButtonState = iNewState; InvalidateRect(&rcButton); } return 0; } LRESULT CLabelContainer::OnMouseDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Only deal with this event if the panel is closable. if (m_hCloseImageList == NULL) return 0; POINT ptMouse = { GET_X_LPARAM(lParam),GET_Y_LPARAM(lParam) }; RECT rcButton,rcClient; GetClientRect(&rcClient); rcButton.top = rcClient.top + LABELCONTAINER_BUTTON_TOPSPACING; rcButton.right = rcClient.right - LABELCONTAINER_BUTTON_RIGHTSPACING; rcButton.bottom = rcButton.top + 16; rcButton.left = rcButton.right - 16; if (::PtInRect(&rcButton,ptMouse)) { m_iButtonState = PANE_BUTTON_DOWN; InvalidateRect(&rcButton); } return 0; } LRESULT CLabelContainer::OnMouseUp(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Only deal with this event if the panel is closable. if (m_hCloseImageList == NULL) return 0; POINT ptMouse = { GET_X_LPARAM(lParam),GET_Y_LPARAM(lParam) }; RECT rcButton,rcClient; GetClientRect(&rcClient); rcButton.top = rcClient.top + LABELCONTAINER_BUTTON_TOPSPACING; rcButton.right = rcClient.right - LABELCONTAINER_BUTTON_RIGHTSPACING; rcButton.bottom = rcButton.top + 16; rcButton.left = rcButton.right - 16; if (::PtInRect(&rcButton,ptMouse)) { if (m_iButtonState == PANE_BUTTON_DOWN && m_hWndCloseHost != NULL) ::PostMessage(m_hWndCloseHost,WM_LABELCONTAINER_CLOSE,0,0); m_iButtonState = PANE_BUTTON_HOVER; InvalidateRect(&rcButton); } else { m_iButtonState = PANE_BUTTON_NORMAL; InvalidateRect(&rcButton); } return 0; } LRESULT CLabelContainer::OnCustomDraw(int idCtrl,LPNMHDR pnmh,BOOL &bHandled) { if (m_hWndCustomDraw != NULL && idCtrl == m_iControlID) return ::SendMessage(m_hWndCustomDraw,WM_CONTROLCUSTOMDRAW,0,(LPARAM)pnmh); bHandled = false; return CDRF_DODEFAULT; } void CLabelContainer::DrawText(CDCHandle dc,RECT *pHeaderRect) { HFONT hOldFont = NULL; if (g_WinVer.m_ulMajorVersion == MAJOR_WINVISTA && g_WinVer.m_ulMinorVersion == MINOR_WINVISTA && g_VisualStyles.IsThemeActive()) { hOldFont = (HFONT)SelectObject(dc,AtlGetDefaultGuiFont()); ::SetBkMode(dc,TRANSPARENT); ::SetTextColor(dc,RGB(139,139,139)); } else { HFONT hFont = AtlCreateBoldFont(AtlGetDefaultGuiFont()); hOldFont = (HFONT)SelectObject(dc,hFont); ::SetBkMode(dc,TRANSPARENT); ::SetTextColor(dc,::GetSysColor(COLOR_BTNFACE)); } RECT rcText; rcText.left = pHeaderRect->left + 3; rcText.right = pHeaderRect->right; rcText.top = pHeaderRect->top + LABELCONTAINER_BORDER_HEIGHT + 1; rcText.bottom = pHeaderRect->bottom; ::DrawText(dc,m_szLabelText,lstrlen(m_szLabelText),&rcText, DT_LEFT | DT_END_ELLIPSIS | DT_SINGLELINE); if (hOldFont != NULL) SelectObject(dc,hOldFont); } void CLabelContainer::DrawBackground(CDCHandle dc,RECT *pHeaderRect) { RECT rcMisc; rcMisc.left = pHeaderRect->left; rcMisc.right = pHeaderRect->right; // Bottom border. rcMisc.top = pHeaderRect->bottom - LABELCONTAINER_BOTTOMBORDER_HEIGHT; rcMisc.bottom = pHeaderRect->bottom; FillRect(dc,&rcMisc,GetSysColorBrush(COLOR_BTNFACE)); if (g_WinVer.m_ulMajorVersion == MAJOR_WINVISTA && g_WinVer.m_ulMinorVersion == MINOR_WINVISTA && g_VisualStyles.IsThemeActive()) { // Gradient background. rcMisc.top = pHeaderRect->top; rcMisc.bottom = pHeaderRect->bottom - LABELCONTAINER_BOTTOMBORDER_HEIGHT; DrawHorGradientRect(dc.m_hDC,&rcMisc,LABELCONTAINER_COLOR_BACKGROUNDVISTA,GetSysColor(COLOR_BTNFACE)); } else if (true) { // Gradient background. rcMisc.top = pHeaderRect->top; rcMisc.bottom = pHeaderRect->bottom - LABELCONTAINER_BOTTOMBORDER_HEIGHT; DrawHorGradientRect(dc.m_hDC,&rcMisc,LABELCONTAINER_COLOR_BACKGROUNDALT,GetSysColor(COLOR_BTNFACE)); } else { // Gradient background. rcMisc.left = LABELCONTAINER_BORDER_HEIGHT; rcMisc.top = pHeaderRect->top + LABELCONTAINER_BORDER_HEIGHT; rcMisc.bottom = pHeaderRect->bottom - LABELCONTAINER_BOTTOMBORDER_HEIGHT - LABELCONTAINER_BORDER_HEIGHT; DrawHorGradientRect(dc.m_hDC,&rcMisc,LABELCONTAINER_COLOR_BACKGROUND,GetSysColor(COLOR_BTNFACE)); // Border lines. rcMisc.left = pHeaderRect->left; rcMisc.top = pHeaderRect->top; rcMisc.bottom = pHeaderRect->top + LABELCONTAINER_BORDER_HEIGHT; DrawHorGradientRect(dc.m_hDC,&rcMisc,LABELCONTAINER_COLOR_BORDER,GetSysColor(COLOR_BTNFACE)); rcMisc.top = pHeaderRect->bottom - LABELCONTAINER_BORDER_HEIGHT - LABELCONTAINER_BOTTOMBORDER_HEIGHT; rcMisc.bottom = pHeaderRect->bottom - LABELCONTAINER_BOTTOMBORDER_HEIGHT; DrawHorGradientRect(dc.m_hDC,&rcMisc,LABELCONTAINER_COLOR_BORDER,GetSysColor(COLOR_BTNFACE)); rcMisc.top = pHeaderRect->top; rcMisc.bottom = pHeaderRect->bottom - LABELCONTAINER_BOTTOMBORDER_HEIGHT; rcMisc.right = pHeaderRect->left + LABELCONTAINER_BORDER_HEIGHT; FillRect(dc,&rcMisc,m_hBorderBrush); } } void CLabelContainer::DrawButton(CDCHandle dc,RECT *pHeaderRect) { if (m_hCloseImageList != NULL) { ImageList_Draw(m_hCloseImageList,m_iButtonState,dc, pHeaderRect->right - 16 - LABELCONTAINER_BUTTON_RIGHTSPACING, LABELCONTAINER_BUTTON_TOPSPACING,ILD_TRANSPARENT); } } void CLabelContainer::SetHeaderHeight(int iHeight) { m_iHeaderHeight = iHeight; } void CLabelContainer::SetLabelText(const TCHAR *szText) { lstrcpy(m_szLabelText,szText); } ================================================ FILE: src/app/control/label_container.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #define LABELCONTAINER_COLOR_BACKGROUND RGB(255,255,255) #define LABELCONTAINER_COLOR_BORDER RGB(64,154,222) #define LABELCONTAINER_COLOR_BACKGROUNDVISTA RGB(252,252,252) #define LABELCONTAINER_COLOR_BACKGROUNDALT ::GetSysColor(COLOR_BTNSHADOW) #define LABELCONTAINER_BOTTOMBORDER_HEIGHT 4 #define LABELCONTAINER_BORDER_HEIGHT 1 #define LABELCONTAINER_MAXTEXT 32 #define LABELCONTAINER_BUTTON_TOPSPACING 1 #define LABELCONTAINER_BUTTON_RIGHTSPACING 0 #define PANE_BUTTON_NORMAL 0 #define PANE_BUTTON_HOVER 1 #define PANE_BUTTON_DOWN 2 #define PANE_BUTTON_DISABLED 3 class CLabelContainer : public CWindowImpl { private: CWindow m_ClientWindow; int m_iHeaderHeight; HBRUSH m_hBorderBrush; TCHAR m_szLabelText[LABELCONTAINER_MAXTEXT]; // Button related. HIMAGELIST m_hCloseImageList; int m_iButtonState; bool m_bButtonDown; // Handle to the control that should receivce custom draw messages. HWND m_hWndCustomDraw; int m_iControlID; // The host window that should receive the close message. HWND m_hWndCloseHost; void InitializeImageList(); void DrawText(CDCHandle dc,RECT *pHeaderRect); void DrawBackground(CDCHandle dc,RECT *pHeaderRect); void DrawButton(CDCHandle dc,RECT *pHeaderRect); public: static CWndClassInfo &GetWndClassInfo() { static CWndClassInfo wc = { { sizeof(WNDCLASSEX),CS_DBLCLKS, StartWindowProc,0,0,NULL,NULL,NULL, GetSysColorBrush(COLOR_BTNFACE),NULL, _T("ckLabelContainer"),NULL }, NULL,NULL,IDC_ARROW,TRUE,0,_T("") }; return wc; } CLabelContainer(bool bClosable = false); ~CLabelContainer(); BEGIN_MSG_MAP(CLabelContainer) MESSAGE_HANDLER(WM_SIZE,OnSize) MESSAGE_HANDLER(WM_SETFOCUS,OnSetFocus) MESSAGE_HANDLER(WM_ERASEBKGND,OnEraseBkgnd) MESSAGE_HANDLER(WM_PAINT,OnPaint) MESSAGE_HANDLER(WM_MOUSEMOVE,OnMouseMove) MESSAGE_HANDLER(WM_LBUTTONDOWN,OnMouseDown) MESSAGE_HANDLER(WM_LBUTTONUP,OnMouseUp) NOTIFY_CODE_HANDLER(NM_CUSTOMDRAW,OnCustomDraw) FORWARD_NOTIFICATIONS() END_MSG_MAP() LRESULT OnSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSetFocus(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnMouseDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnMouseUp(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnCustomDraw(int idCtrl,LPNMHDR pnmh,BOOL &bHandled); void SetCustomDrawHandler(HWND hWndCustomDraw,int iID); void SetClient(HWND hWndClient); void SetCloseHost(HWND hWndCloseHost); void UpdateLayout(); void UpdateLayout(int iWidth,int iHeight); void SetHeaderHeight(int iHeight); void SetLabelText(const TCHAR *szText); }; ================================================ FILE: src/app/control/mini_html_ctrl.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "mini_html_ctrl.hh" HBRUSH CMiniHtmlCtrl::m_hBackgroundBrush = NULL; CMiniHtmlCtrl::CMiniHtmlCtrl() { m_pDocBuffer = NULL; m_ulDocLength = 0; //Load(_T("C:\\Users\\Christian Kindahl\\Desktop\\Active Projects\\InfraRecorder\\trunk\\Binary64\\Test.xml")); // Create fonts. m_hNormalFont = NULL; m_hBoldFont = NULL; m_hHeaderFont = NULL; LOGFONT lf = { 0 }; if (::GetObject(AtlGetDefaultGuiFont(),sizeof(LOGFONT),&lf) == sizeof(LOGFONT)) { lf.lfHeight = MINIHTML_FONTHEIGHT_NORMAL; lstrcpy(lf.lfFaceName,_T("Verdana")); m_hNormalFont = ::CreateFontIndirect(&lf); } if (m_hNormalFont == NULL) m_hNormalFont = AtlGetDefaultGuiFont(); m_hBoldFont = AtlCreateBoldFont(m_hNormalFont); lf.lfItalic = 1; m_hItalicFont = ::CreateFontIndirect(&lf); if (m_hItalicFont == NULL) m_hItalicFont = m_hNormalFont; lf.lfItalic = 0; lf.lfHeight = MINIHTML_FONTHEIGHT_HEADER; m_hHeaderFont = AtlCreateBoldFont(::CreateFontIndirect(&lf)); if (m_hHeaderFont == NULL) m_hHeaderFont = m_hBoldFont; // Create the background brush. if (m_hBackgroundBrush == NULL) m_hBackgroundBrush = ::CreateSolidBrush(MINIHTML_COLOR_BACKGROUND); // Set default font widths to zer. m_uiNormalSpaceWidth = 0; m_uiBoldSpaceWidth = 0; m_uiItalicSpaceWidth = 0; m_uiHeaderSpaceWidth = 0; } CMiniHtmlCtrl::~CMiniHtmlCtrl() { // Close any opened document. Close(); if (m_hNormalFont != AtlGetDefaultGuiFont()) ::DeleteObject(m_hNormalFont); if (m_hBoldFont != NULL) ::DeleteObject(m_hBoldFont); if (m_hItalicFont != NULL) ::DeleteObject(m_hItalicFont); if (m_hHeaderFont != NULL) ::DeleteObject(m_hHeaderFont); // Delete the background brush. if (m_hBackgroundBrush != NULL) { ::DeleteObject(m_hBackgroundBrush); m_hBackgroundBrush = NULL; } } bool CMiniHtmlCtrl::Load(const TCHAR *szFileName) { Close(); ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_READ)) return false; // Make sure that the file is not too large. if (File.size() > 0xFFFFFFFF) return false; // If the application is in an unicode environment we need to check what // byte-order us used. unsigned short usBOM = 0; if (File.read(&usBOM,2) == -1) return false; switch (usBOM) { // Currently the only supported byte-order. case BOM_UTF32BE: break; case BOM_UTF8: case BOM_UTF32LE: case BOM_SCSU: return false; default: // If no BOM is found the file pointer has to be re-moved to the beginning. File.seek(0,ckcore::File::ckFILE_BEGIN); break; }; unsigned long ulFileSize = (unsigned long)File.size() - (unsigned long)File.tell(); m_ulDocLength = ulFileSize / sizeof(TCHAR); m_pDocBuffer = new TCHAR[m_ulDocLength + 1]; if (File.read(m_pDocBuffer,ulFileSize) == -1) return false; m_pDocBuffer[m_ulDocLength] = '\0'; return ParseBuffer(); } CMiniHtmlCtrl::eTagType CMiniHtmlCtrl::ParseTag(const TCHAR *szTag) { if (!lstrcmp(szTag,_T("h")) || !lstrcmp(szTag,_T("H"))) return TT_HEADER; else if (!lstrcmp(szTag,_T("b")) || !lstrcmp(szTag,_T("B"))) return TT_BOLD; else if (!lstrcmp(szTag,_T("i")) || !lstrcmp(szTag,_T("I"))) return TT_ITALIC; else if (!lstrcmp(szTag,_T("br")) || !lstrcmp(szTag,_T("BR"))) return TT_BREAK; return TT_UNKNOWN; } CMiniHtmlCtrl::eAtomAttr CMiniHtmlCtrl::TagToAttr(eTagType TagType) { switch (TagType) { case TT_BOLD: return AA_BOLD; case TT_ITALIC: return AA_ITALIC; case TT_HEADER: return AA_HEADER; } return AA_NORMAL; } bool CMiniHtmlCtrl::ParseBuffer() { bool bInTag = false; tstring Tag; std::vector Tags; Tags.push_back(TT_NORMAL); int iWordStart = -1; for (unsigned int i = 0; i < m_ulDocLength; i++) { // Ignore some characters. if (m_pDocBuffer[i] == '\t' || m_pDocBuffer[i] == '\n' || m_pDocBuffer[i] == '\r') { if (iWordStart != -1) { eTagType CurTag = Tags[Tags.size() - 1]; m_Atoms.push_back(CAtom(m_pDocBuffer + iWordStart,i - iWordStart, AT_TEXT,TagToAttr(CurTag))); TCHAR szTemp[64]; lstrncpy(szTemp,m_pDocBuffer + iWordStart,i - iWordStart); szTemp[i - iWordStart] = '\0'; ::MessageBox(NULL,szTemp,_T(""),MB_OK); iWordStart = -1; } continue; } if (bInTag) { if (m_pDocBuffer[i] == '>') { // Check if it's an ending tag. if (Tag.c_str()[0] == '/') { if (iWordStart != -1) { eTagType CurTag = Tags[Tags.size() - 1]; m_Atoms.push_back(CAtom(m_pDocBuffer + iWordStart, i - iWordStart - (unsigned int)Tag.size() - 1,AT_TEXT,TagToAttr(CurTag))); TCHAR szTemp[64]; lstrncpy(szTemp,m_pDocBuffer + iWordStart,i - iWordStart - Tag.size() - 1); szTemp[i - iWordStart - Tag.size() - 1] = '\0'; iWordStart = -1; } // Pop the tag stack if necessary. if (Tags[Tags.size() - 1] == ParseTag(Tag.c_str() + 1)) Tags.pop_back(); Tag.erase(); } else if (Tag[Tag.size() - 1] == '/') // Check if we have a self-terminating tag. { if (iWordStart != -1) { eTagType CurTag = Tags[Tags.size() - 1]; m_Atoms.push_back(CAtom(m_pDocBuffer + iWordStart, i - iWordStart - (unsigned int)Tag.size() - 1,AT_TEXT,TagToAttr(CurTag))); TCHAR szTemp[64]; lstrncpy(szTemp,m_pDocBuffer + iWordStart,i - iWordStart - Tag.size() - 1); szTemp[i - iWordStart - Tag.size() - 1] = '\0'; iWordStart = -1; } Tag.resize(Tag.size() - 1); eTagType CurTag = ParseTag(Tag.c_str()); switch (CurTag) { case TT_BREAK: { // Make sure that the break will be of correct height. eAtomAttr BreakAttr = Tags.size() > 0 ? TagToAttr(Tags[Tags.size() - 1]) : AA_NORMAL; m_Atoms.push_back(CAtom(NULL,NULL,AT_BREAK,BreakAttr)); } break; } Tag.erase(); } else { // We have found a new tag and not processed the last atom, process it. if (iWordStart != -1) { eTagType CurTag = Tags[Tags.size() - 1]; m_Atoms.push_back(CAtom(m_pDocBuffer + iWordStart, i - iWordStart - (unsigned int)Tag.size() - 1,AT_TEXT,TagToAttr(CurTag))); TCHAR szTemp[64]; lstrncpy(szTemp,m_pDocBuffer + iWordStart,i - iWordStart - Tag.size() - 1); szTemp[i - iWordStart - Tag.size() - 1] = '\0'; iWordStart = -1; } eTagType TagType = ParseTag(Tag.c_str()); Tags.push_back(TagType); Tag.erase(); } bInTag = false; } else { Tag.push_back(m_pDocBuffer[i]); } } else { if (m_pDocBuffer[i] == '<') { bInTag = true; } else { if (m_pDocBuffer[i] == ' ') { if (iWordStart != -1) { eTagType CurTag = Tags[Tags.size() - 1]; m_Atoms.push_back(CAtom(m_pDocBuffer + iWordStart,i - iWordStart, AT_TEXT,TagToAttr(CurTag))); TCHAR szTemp[64]; lstrncpy(szTemp,m_pDocBuffer + iWordStart,i - iWordStart); szTemp[i - iWordStart] = '\0'; iWordStart = -1; } } else { if (iWordStart == -1) iWordStart = i; } } } } if (iWordStart != -1) { eTagType CurTag = Tags[Tags.size() - 1]; m_Atoms.push_back(CAtom(m_pDocBuffer + iWordStart,m_ulDocLength - iWordStart, AT_TEXT,TagToAttr(CurTag))); TCHAR szTemp[64]; lstrncpy(szTemp,m_pDocBuffer + iWordStart,m_ulDocLength - iWordStart); szTemp[m_ulDocLength - iWordStart] = '\0'; } return true; } void CMiniHtmlCtrl::Close() { if (m_pDocBuffer != NULL) { delete [] m_pDocBuffer; m_pDocBuffer = NULL; } m_ulDocLength = 0; } HFONT CMiniHtmlCtrl::GetAtomFont(const CAtom *pAtom) { switch (pAtom->m_Attr) { case AA_HEADER: return m_hHeaderFont; case AA_BOLD: return m_hBoldFont; case AA_ITALIC: return m_hItalicFont; default: return m_hNormalFont; } } unsigned int CMiniHtmlCtrl::GetAtomWidth(const CAtom *pAtom) { if (pAtom->m_Type == AT_BREAK) return 0; // Draw the text. HDC hDC = GetDC(); HFONT hOldFont = (HFONT)SelectObject(hDC,GetAtomFont(pAtom)); RECT rcText = { 0,0,0,0 }; DrawText(hDC,pAtom->m_szText,pAtom->m_uiTextLen,&rcText,DT_LEFT | DT_CALCRECT); SelectObject(hDC,hOldFont); return rcText.right; } unsigned int CMiniHtmlCtrl::GetAtomSpaceWidth(const CAtom *pAtom) { switch (pAtom->m_Attr) { case AA_HEADER: if (m_uiHeaderSpaceWidth != 0) return m_uiHeaderSpaceWidth; break; case AA_BOLD: if (m_uiBoldSpaceWidth != 0) return m_uiBoldSpaceWidth; break; case AA_ITALIC: if (m_uiItalicSpaceWidth != 0) return m_uiItalicSpaceWidth; break; default: if (m_uiNormalSpaceWidth != 0) return m_uiNormalSpaceWidth; break; } HDC hDC = GetDC(); HFONT hOldFont = (HFONT)SelectObject(hDC,GetAtomFont(pAtom)); RECT rcText = { 0,0,0,0 }; DrawText(hDC,_T(" "),1,&rcText,DT_LEFT | DT_CALCRECT); SelectObject(hDC,hOldFont); switch (pAtom->m_Attr) { case AA_HEADER: m_uiHeaderSpaceWidth = rcText.right; break; case AA_BOLD: m_uiBoldSpaceWidth = rcText.right; break; case AA_ITALIC: m_uiItalicSpaceWidth = rcText.right; break; default: m_uiNormalSpaceWidth = rcText.right; break; } return rcText.right; } unsigned int CMiniHtmlCtrl::GetAtomsTotalWidth(unsigned int uiFirstAtom, unsigned int uiLastAtom) { unsigned int uiTotalWidth = 0; for (unsigned int uiAtom = uiFirstAtom; uiAtom < uiLastAtom; uiAtom++) { // Safety precausion. if (uiAtom >= m_Atoms.size()) break; CAtom *pAtom = &m_Atoms[uiAtom]; if (pAtom->m_Type == AT_BREAK) continue; uiTotalWidth += pAtom->m_uiWidth; if (uiAtom != uiFirstAtom) uiTotalWidth += GetAtomSpaceWidth(pAtom); } return uiTotalWidth; } int CMiniHtmlCtrl::RenderText(CDCHandle dc,const RECT *pRect,const CAtom *pAtom) { // Draw the text. HFONT hOldFont = (HFONT)SelectObject(dc,GetAtomFont(pAtom)); ::SetBkMode(dc,TRANSPARENT); ::SetTextColor(dc,::GetSysColor(COLOR_WINDOWTEXT)); RECT rcText = *pRect; ::DrawText(dc,pAtom->m_szText,pAtom->m_uiTextLen,&rcText,DT_LEFT); // Calculate text height. int iTextHeight = DrawText(dc,pAtom->m_szText,pAtom->m_uiTextLen,&rcText,DT_LEFT | DT_CALCRECT); if (hOldFont != NULL) SelectObject(dc,hOldFont); return iTextHeight; } int CMiniHtmlCtrl::RenderImage(CDCHandle dc,const RECT *pRect,const CAtom *pAtom) { return 0; } void CMiniHtmlCtrl::Render(CDCHandle dc) { RECT rcClient; GetClientRect(&rcClient); rcClient.right -= MINIHTML_HORIZONTAL_INDENT; unsigned int uiAtom = 0; unsigned int uiMaxHeight = 0,uiCurHeight = 0; // Render all lines. std::vector::const_iterator itLine; for (itLine = m_LineWordCount.begin(); itLine != m_LineWordCount.end(); itLine++) { rcClient.left = MINIHTML_HORIZONTAL_INDENT; uiMaxHeight = 0; // Check if we should center the line. if (uiAtom < m_Atoms.size() && m_Atoms[uiAtom].m_Attr == AA_HEADER) { rcClient.left = MINIHTML_HORIZONTAL_INDENT + ((rcClient.right - GetAtomsTotalWidth(uiAtom,uiAtom + *itLine)) >> 1); } // Render all words on the line. for (unsigned int i = 0; i < *itLine; i++,uiAtom++) { // Safety precausion. if (uiAtom >= m_Atoms.size()) break; CAtom *pAtom = &m_Atoms[uiAtom]; if (pAtom->m_Type == AT_BREAK) { uiMaxHeight = pAtom->m_Attr == AA_HEADER ? MINIHTML_FONTHEIGHT_HEADER : MINIHTML_FONTHEIGHT_NORMAL; continue; } switch (pAtom->m_Type) { case AT_TEXT: uiCurHeight = RenderText(dc,&rcClient,pAtom); break; case AT_IMAGE: uiCurHeight = RenderImage(dc,&rcClient,pAtom); break; } if (uiCurHeight > uiMaxHeight) uiMaxHeight = uiCurHeight; rcClient.left += pAtom->m_uiWidth + GetAtomSpaceWidth(pAtom); } rcClient.top += uiMaxHeight; } } void CMiniHtmlCtrl::Layout(unsigned int uiWidth,unsigned int uiHeight) { if (uiWidth == 0) return; // Remove the indentation and border from the specified width immediately. uiWidth -= (MINIHTML_HORIZONTAL_INDENT << 1) + (GetSystemMetrics(SM_CXEDGE) << 1); m_LineWordCount.clear(); unsigned int uiLeft = 0,uiLine = 0; unsigned int uiWordCount = 0; unsigned int uiSpaceWidth = 0; std::vector::iterator itAtom; for (itAtom = m_Atoms.begin(); itAtom != m_Atoms.end(); itAtom++) { if (itAtom->m_Type == AT_BREAK) { itAtom->m_uiLine = uiLine++; uiLeft = 0; m_LineWordCount.push_back(uiWordCount + 1); uiWordCount = 0; continue; } // Calculate the width of a space character. uiSpaceWidth = GetAtomSpaceWidth(&(*itAtom)); if (itAtom->m_uiWidth == 0) itAtom->m_uiWidth = GetAtomWidth(&(*itAtom)); if ((uiLeft + itAtom->m_uiWidth) <= uiWidth) { itAtom->m_uiLine = uiLine; if (uiLeft != 0) uiLeft += uiSpaceWidth; uiLeft += itAtom->m_uiWidth; uiWordCount++; } else { itAtom->m_uiLine = ++uiLine; uiLeft = itAtom->m_uiWidth; m_LineWordCount.push_back(uiWordCount); uiWordCount = 1; } } if (uiLeft != 0) { m_LineWordCount.push_back(uiWordCount); } RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); } LRESULT CMiniHtmlCtrl::OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (wParam != NULL) { HDC hDC = (HDC)wParam; Render(hDC); ReleaseDC(hDC); } else { CPaintDC dc(m_hWnd); Render(dc.m_hDC); ReleaseDC(dc); } return 0; } LRESULT CMiniHtmlCtrl::OnSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { unsigned int uiWidth = GET_X_LPARAM(lParam); unsigned int uiHeight = GET_Y_LPARAM(lParam); Layout(uiWidth,uiHeight); return 0; } ================================================ FILE: src/app/control/mini_html_ctrl.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #define MINIHTML_HORIZONTAL_INDENT 3 #define MINIHTML_COLOR_BACKGROUND RGB(245,245,245) #define MINIHTML_FONTHEIGHT_NORMAL 12 #define MINIHTML_FONTHEIGHT_HEADER 18 #define BOM_UTF8 0xEFBBBF #define BOM_UTF32BE 0x0000FEFF #define BOM_UTF32LE 0xFFFE0000 #define BOM_SCSU 0x0EFEFF class CMiniHtmlCtrl : public CScrollWindowImpl { private: enum eAtomType { AT_TEXT, AT_IMAGE, AT_BREAK }; enum eAtomAttr { AA_NORMAL, AA_BOLD, AA_ITALIC, AA_HEADER }; enum eTagType { TT_UNKNOWN, TT_NORMAL, TT_BOLD, TT_ITALIC, TT_HEADER, TT_BREAK }; class CAtom { public: TCHAR *m_szText; unsigned int m_uiTextLen; unsigned int m_uiWidth; unsigned int m_uiLine; CMiniHtmlCtrl::eAtomType m_Type; CMiniHtmlCtrl::eAtomAttr m_Attr; CAtom(TCHAR *szText,unsigned int uiTextLen,CMiniHtmlCtrl::eAtomType Type, CMiniHtmlCtrl::eAtomAttr Attr) { m_szText = szText; m_uiTextLen = uiTextLen; m_uiWidth = 0; m_uiLine = 0; m_Type = Type; m_Attr = Attr; } }; TCHAR *m_pDocBuffer; unsigned long m_ulDocLength; std::vector m_Atoms; std::vector m_LineWordCount; HFONT m_hNormalFont; HFONT m_hBoldFont; HFONT m_hItalicFont; HFONT m_hHeaderFont; unsigned int m_uiNormalSpaceWidth; unsigned int m_uiBoldSpaceWidth; unsigned int m_uiItalicSpaceWidth; unsigned int m_uiHeaderSpaceWidth; static HBRUSH m_hBackgroundBrush; HFONT GetAtomFont(const CAtom *pAtom); unsigned int GetAtomWidth(const CAtom *pAtom); unsigned int GetAtomSpaceWidth(const CAtom *pAtom); unsigned int GetAtomsTotalWidth(unsigned int uiFirstAtom,unsigned int uiLastAtom); int RenderText(CDCHandle dc,const RECT *pRect,const CAtom *pAtom); int RenderImage(CDCHandle dc,const RECT *pRect,const CAtom *pAtom); void Render(CDCHandle dc); void Layout(unsigned int uiWidth,unsigned int uiHeight); eTagType ParseTag(const TCHAR *szTag); eAtomAttr TagToAttr(eTagType TagType); bool ParseBuffer(); public: static CWndClassInfo &GetWndClassInfo() { static CWndClassInfo wc = { { sizeof(WNDCLASSEX),CS_DBLCLKS, StartWindowProc,0,0,NULL,NULL,NULL, m_hBackgroundBrush,NULL, _T("ckMiniHTML"),NULL }, NULL,NULL,IDC_ARROW,TRUE,0,_T("") }; return wc; } CMiniHtmlCtrl(); ~CMiniHtmlCtrl(); bool Load(const TCHAR *szFileName); void Close(); BEGIN_MSG_MAP(CMiniHtmlCtrl) MESSAGE_HANDLER(WM_PAINT,OnPaint) MESSAGE_HANDLER(WM_SIZE,OnSize) DEFAULT_REFLECTION_HANDLER() CHAIN_MSG_MAP(CScrollWindowImpl) END_MSG_MAP() LRESULT OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/control/project_list_view_ctrl.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_list_view_ctrl.hh" #include "project_manager.hh" #include "settings.hh" #include "main_frm.hh" #include "string_table.hh" #include "project_drop_source.hh" #include "project_data_object.hh" /* FIXME: For Windows XP and newer. #ifndef LVM_SETSELECTEDCOLUMN #define LVM_SETSELECTEDCOLUMN (LVM_FIRST + 140) #endif ::SendMessage(m_hWnd,LVM_SETSELECTEDCOLUMN,0,0); */ CProjectListViewDropTarget::CProjectListViewDropTarget(CProjectListViewCtrl *pHost) { m_pHost = pHost; } bool CProjectListViewDropTarget::OnDragOver(POINTL ptCursor) { LVHITTESTINFO lvHit; lvHit.pt.x = ptCursor.x; lvHit.pt.y = ptCursor.y; ScreenToClient(m_pHost->m_hWnd,&lvHit.pt); // See we're dragging above a folder, in that case highlight it. int iTarget = m_pHost->HitTest(&lvHit); if (iTarget != -1 && (((CItemData *)m_pHost->GetItemData(iTarget))->ucFlags & PROJECTITEM_FLAG_ISFOLDER)) m_pHost->SelectDropTarget(iTarget); else m_pHost->SelectDropTarget(-1); return true; } bool CProjectListViewDropTarget::OnDrop(POINTL ptCursor,IDataObject *pDataObject) { CWaitCursor WaitCursor; // This displays the hourglass cursor. LVHITTESTINFO lvHit; lvHit.pt.x = ptCursor.x; lvHit.pt.y = ptCursor.y; ScreenToClient(m_pHost->m_hWnd,&lvHit.pt); CProjectNode *pTargetNode = NULL; int iTarget = m_pHost->HitTest(&lvHit); if (iTarget != -1 && (((CItemData *)m_pHost->GetItemData(iTarget))->ucFlags & PROJECTITEM_FLAG_ISFOLDER)) { m_pHost->SelectDropTarget(-1); pTargetNode = g_TreeManager.ResolveNode(g_TreeManager.GetCurrentNode(), (CItemData *)m_pHost->GetItemData(iTarget)); } // Handle the data. HandleDropData(pDataObject,pTargetNode,ptCursor); return true; } void CProjectListViewDropTarget::OnDragLeave() { m_pHost->SelectDropTarget(-1); } bool CProjectListViewDropTarget::HandleDropData(IDataObject *pDataObject,CProjectNode *pTargetNode, POINTL ptCursor) { // Construct a FORMATETC object. FORMATETC FormatEtc = { CF_HDROP, 0, DVASPECT_CONTENT, -1, TYMED_HGLOBAL }; STGMEDIUM StgMedium; if (pDataObject->QueryGetData(&FormatEtc) == S_OK) { if (pDataObject->GetData(&FormatEtc,&StgMedium) == S_OK) { // Prepare a project file transaction. CProjectManager::CFileTransaction Transaction; HDROP hDrop = (HDROP)GlobalLock(StgMedium.hGlobal); unsigned int uiNumFiles = DragQueryFile(hDrop,0xFFFFFFFF,NULL,NULL); TCHAR szFullName[MAX_PATH]; for (unsigned int i = 0; i < uiNumFiles; i++) { // Add each file to the project. if (DragQueryFile(hDrop,i,szFullName,MAX_PATH - 1)) Transaction.AddFile(szFullName,pTargetNode); } GlobalUnlock(StgMedium.hGlobal); ReleaseStgMedium(&StgMedium); } } else { // Move to another folder if possible, otherwise rearrange in the list. if (pTargetNode != NULL) { FormatEtc.cfFormat = static_cast(m_uiClipFormat); if (pDataObject->QueryGetData(&FormatEtc) == S_OK) { if (pDataObject->GetData(&FormatEtc,&StgMedium) == S_OK) { // Prepare a project file transaction. CProjectManager::CFileTransaction Transaction; CProjectDropData *pDropData = (CProjectDropData *)GlobalLock(StgMedium.hGlobal); if (pDropData->m_pParent == NULL) return true; SIZE_T uiNumFiles = (GlobalSize(StgMedium.hGlobal) - sizeof(CProjectDropData)) / sizeof(CItemData *); for (SIZE_T i = 0; i < uiNumFiles; i++) { CItemData *pItemData = pDropData->m_ppData[i]; Transaction.MoveFile(pDropData->m_pParent,pItemData,pTargetNode); } GlobalUnlock(StgMedium.hGlobal); ReleaseStgMedium(&StgMedium); } } } else { /* */ // Determine the dropped item. LVHITTESTINFO lvHit; lvHit.pt.x = ptCursor.x; lvHit.pt.y = ptCursor.y; ScreenToClient(m_pHost->m_hWnd,&lvHit.pt); ListView_HitTest(m_pHost->m_hWnd,&lvHit); // Not inside the list view? if (lvHit.iItem == -1) return true; // Make sure that we can't drop a file above a folder. CItemData *pDropItemData = (CItemData *)m_pHost->GetItemData(lvHit.iItem); while (pDropItemData->ucFlags & PROJECTITEM_FLAG_ISFOLDER) pDropItemData = (CItemData *)m_pHost->GetItemData(++lvHit.iItem); CProjectNode *pCurrentNode = g_TreeManager.GetCurrentNode(); // Locate the dropped item (wee need an iterator so we know where to insert // the dropped files. std::list ::iterator itFileObject; for (itFileObject = pCurrentNode->m_Files.begin(); itFileObject != pCurrentNode->m_Files.end(); itFileObject++) { if (*itFileObject == pDropItemData) break; } // Move the selected items. int iItemIndex = -1; iItemIndex = m_pHost->GetNextItem(iItemIndex,LVNI_SELECTED); while (iItemIndex != -1) { // Move the internal item data pointer. CItemData *pItemData = (CItemData *)m_pHost->GetItemData(iItemIndex); pCurrentNode->m_Files.remove(pItemData); pCurrentNode->m_Files.insert(itFileObject,pItemData); // Move the actual list item. LVITEM lvi = { 0 }; lvi.iItem = iItemIndex; lvi.iSubItem = 0; lvi.pszText = LPSTR_TEXTCALLBACK; lvi.stateMask = static_cast(~LVIS_SELECTED); lvi.mask = LVIF_TEXT | LVIF_IMAGE | LVIF_PARAM | LVIF_STATE; m_pHost->GetItem(&lvi); lvi.iItem = lvHit.iItem; // Re-insert the item. int iResult = m_pHost->InsertItem(&lvi); if (lvi.iItem < iItemIndex) lvHit.iItem++; if (iResult <= iItemIndex) iItemIndex++; // Delete the old item. m_pHost->DeleteItem(iItemIndex); iItemIndex = m_pHost->GetNextItem(-1,LVNI_SELECTED); } /* */ } } return true; } /* */ CProjectListViewCtrl::CProjectListViewCtrl() { m_hDragImageList = NULL; // Drop target. m_pDropTarget = new CProjectListViewDropTarget(this); CoLockObjectExternal(m_pDropTarget,TRUE,FALSE); } CProjectListViewCtrl::~CProjectListViewCtrl() { // Drop target. if (m_pDropTarget != NULL) { CoLockObjectExternal(m_pDropTarget,FALSE,TRUE); m_pDropTarget->Release(); m_pDropTarget = NULL; } if (m_hDragImageList != NULL) ImageList_Destroy(m_hDragImageList); } LRESULT CProjectListViewCtrl::OnKeyDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { LRESULT lResult = DefWindowProc(uMsg,wParam,lParam); if (wParam == VK_RETURN) { if (GetSelectedCount() > 0) { // This is not safe, I know. BOOL bDummy; g_pMainFrame->OnPLVDblClk(IDC_PROJECTLISTVIEW,NULL,bDummy); } } return lResult; } LRESULT CProjectListViewCtrl::OnDropFiles(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CWaitCursor WaitCursor; // This displays the hourglass cursor. HDROP hDrop = (HDROP)wParam; POINT ptDrop; TCHAR szFullName[MAX_PATH]; if (DragQueryPoint(hDrop,&ptDrop) > 0) { // Prepare a project file transaction. CProjectManager::CFileTransaction Transaction; unsigned int uiNumFiles = DragQueryFile(hDrop,0xFFFFFFFF,NULL,NULL); for (unsigned int i = 0; i < uiNumFiles; i++) { if (DragQueryFile(hDrop,i,szFullName,MAX_PATH - 1)) Transaction.AddFile(szFullName); } } DragFinish(hDrop); bHandled = false; return 0; } LRESULT CProjectListViewCtrl::OnSetFocus(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { g_ProjectManager.ListSetActive(); g_ProjectManager.NotifyListSelChanged(GetSelectedCount()); bHandled = false; return 0; } LRESULT CProjectListViewCtrl::OnCustomDraw(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { LPNMLVCUSTOMDRAW lpNMCustomDraw = (LPNMLVCUSTOMDRAW)lParam; switch (lpNMCustomDraw->nmcd.dwDrawStage) { case CDDS_PREPAINT: return CDRF_NOTIFYITEMDRAW; case CDDS_ITEMPREPAINT: CItemData *pItemData = (CItemData *)lpNMCustomDraw->nmcd.lItemlParam; if (pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) { lpNMCustomDraw->clrText = PROJECTLISTVIEW_COLOR_IMPORTED; return CDRF_NEWFONT; } if (pItemData->ucFlags & PROJECTITEM_FLAG_ISLOCKED) { lpNMCustomDraw->clrText = GetSysColor(COLOR_GRAYTEXT); return CDRF_NEWFONT; } bHandled = false; return CDRF_DODEFAULT; } bHandled = false; return CDRF_DODEFAULT; } void CProjectListViewCtrl::BeginDrag(LPNMLISTVIEW pNMListView) { CProjectDropSource *pDropSource = new CProjectDropSource(); CProjectDataObject *pDataObject = new CProjectDataObject(); // Add all file names to the data object. int iItemIndex = -1; iItemIndex = GetNextItem(iItemIndex,LVNI_SELECTED); while (iItemIndex != -1) { CItemData *pItemData = (CItemData *)GetItemData(iItemIndex); pDataObject->AddFile(pItemData); iItemIndex = GetNextItem(iItemIndex,LVNI_SELECTED); } pDataObject->SetParent(g_TreeManager.GetCurrentNode()); DWORD dwEffect = 0; ::DoDragDrop(pDataObject,pDropSource,DROPEFFECT_MOVE,&dwEffect); pDropSource->Release(); pDataObject->Release(); } void CProjectListViewCtrl::SetViewStyle(int iViewStyle) { unsigned long ulStyle = 0; switch (iViewStyle) { case LISTVIEWSTYLE_LARGEICONS: ulStyle = LVS_ICON; break; case LISTVIEWSTYLE_SMALLICONS: ulStyle = LVS_SMALLICON; break; case LISTVIEWSTYLE_LIST: ulStyle = LVS_LIST; break; case LISTVIEWSTYLE_DETAILS: ulStyle = LVS_REPORT; break; }; unsigned long ulOldStyle = GetWindowLong(GWL_STYLE); if ((ulOldStyle & LVS_TYPEMASK) != ulStyle) { unsigned long ulNewStyle = (ulOldStyle & ~LVS_TYPEMASK) | ulStyle; SetWindowLong(GWL_STYLE,ulNewStyle); } } LRESULT CProjectListViewCtrl::OnViewLargeIcons(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_DynamicSettings.m_iPrjListViewStyle = LISTVIEWSTYLE_LARGEICONS; g_DynamicSettings.Apply(); return 0; } LRESULT CProjectListViewCtrl::OnViewSmallIcons(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_DynamicSettings.m_iPrjListViewStyle = LISTVIEWSTYLE_SMALLICONS; g_DynamicSettings.Apply(); return 0; } LRESULT CProjectListViewCtrl::OnViewList(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_DynamicSettings.m_iPrjListViewStyle = LISTVIEWSTYLE_LIST; g_DynamicSettings.Apply(); return 0; } LRESULT CProjectListViewCtrl::OnViewDetails(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_DynamicSettings.m_iPrjListViewStyle = LISTVIEWSTYLE_DETAILS; g_DynamicSettings.Apply(); return 0; } LRESULT CProjectListViewCtrl::OnNewFolder(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_ProjectManager.ListAddNewFolder(); return 0; } /* CProjectListViewCtrl::SelectDropTarget -------------------------------------- Marks the specified item as drop target, if iDropItemIndex the drop target items will be cleared but no new target selected. */ void CProjectListViewCtrl::SelectDropTarget(int iDropItemIndex) { // Move the selected items. int iItemIndex = -1; iItemIndex = GetNextItem(iItemIndex,LVNI_DROPHILITED); while (iItemIndex != -1) { SetItemState(iItemIndex,0,LVNI_DROPHILITED); iItemIndex = GetNextItem(-1,LVNI_DROPHILITED); } if (iDropItemIndex != -1) SetItemState(iDropItemIndex,LVNI_DROPHILITED,LVNI_DROPHILITED); } void CProjectListViewCtrl::ForceRedraw() { RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient,true); } ================================================ FILE: src/app/control/project_list_view_ctrl.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "ctrl_messages.hh" #include "tree_manager.hh" #include "project_drop_target_base.hh" // Color of items flagged as imported. #define PROJECTLISTVIEW_COLOR_IMPORTED RGB(92,53,102) class CProjectListViewCtrl; class CProjectListViewDropTarget : public CProjectDropTargetBase { private: CProjectListViewCtrl *m_pHost; bool HandleDropData(IDataObject *pDataObject,CProjectNode *pTargetNode,POINTL ptCursor); public: CProjectListViewDropTarget(CProjectListViewCtrl *pHost); bool OnDragOver(POINTL ptCursor); bool OnDrop(POINTL ptCursor,IDataObject *pDataObject); void OnDragLeave(); }; class CProjectListViewCtrl : public CWindowImpl { private: HIMAGELIST m_hDragImageList; public: CProjectListViewDropTarget *m_pDropTarget; DECLARE_WND_CLASS(_T("ckProjectListViewCtrl")); CProjectListViewCtrl(); ~CProjectListViewCtrl(); void SetViewStyle(int iViewStyle); void BeginDrag(LPNMLISTVIEW pNMListView); BEGIN_MSG_MAP(CProjectListViewCtrl) COMMAND_ID_HANDLER(ID_VIEW_LARGEICONS,OnViewLargeIcons) COMMAND_ID_HANDLER(ID_VIEW_SMALLICONS,OnViewSmallIcons) COMMAND_ID_HANDLER(ID_VIEW_LIST,OnViewList) COMMAND_ID_HANDLER(ID_VIEW_DETAILS,OnViewDetails) COMMAND_ID_HANDLER(ID_EDIT_NEWFOLDER,OnNewFolder) MESSAGE_HANDLER(WM_KEYDOWN,OnKeyDown) MESSAGE_HANDLER(WM_DROPFILES,OnDropFiles) MESSAGE_HANDLER(WM_SETFOCUS,OnSetFocus) MESSAGE_HANDLER(WM_CONTROLCUSTOMDRAW,OnCustomDraw) END_MSG_MAP() LRESULT OnKeyDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnDropFiles(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSetFocus(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnCustomDraw(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnViewLargeIcons(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnViewSmallIcons(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnViewList(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnViewDetails(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnNewFolder(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); void ForceRedraw(); void SelectDropTarget(int iDropItemIndex); }; ================================================ FILE: src/app/control/project_tree_view_ctrl.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_tree_view_ctrl.hh" #include "project_manager.hh" #include "project_data_object.hh" #include "project_drop_source.hh" CProjectTreeViewDropTarget::CProjectTreeViewDropTarget(CTreeViewCtrlEx *pHost) { m_pHost = pHost; } bool CProjectTreeViewDropTarget::OnDragOver(POINTL ptCursor) { TVHITTESTINFO tvHit; tvHit.pt.x = ptCursor.x; tvHit.pt.y = ptCursor.y; ScreenToClient(m_pHost->m_hWnd,&tvHit.pt); HTREEITEM hTarget = m_pHost->HitTest(&tvHit); if (hTarget) { m_pHost->SelectDropTarget(hTarget); return true; } m_pHost->SelectDropTarget(NULL); return false; } bool CProjectTreeViewDropTarget::OnDrop(POINTL ptCursor,IDataObject *pDataObject) { CWaitCursor WaitCursor; // This displays the hourglass cursor. TVHITTESTINFO tvHit; tvHit.pt.x = ptCursor.x; tvHit.pt.y = ptCursor.y; ScreenToClient(m_pHost->m_hWnd,&tvHit.pt); HTREEITEM hTarget = m_pHost->HitTest(&tvHit); if (hTarget) { m_pHost->SelectDropTarget(NULL); HandleDropData(pDataObject,(CProjectNode *)m_pHost->GetItemData(hTarget)); return true; } return false; } void CProjectTreeViewDropTarget::OnDragLeave() { m_pHost->SelectDropTarget(NULL); } bool CProjectTreeViewDropTarget::HandleDropData(IDataObject *pDataObject,CProjectNode *pTargetNode) { // Construct a FORMATETC object. FORMATETC FormatEtc = { CF_HDROP, 0, DVASPECT_CONTENT, -1, TYMED_HGLOBAL }; STGMEDIUM StgMedium; if (pDataObject->QueryGetData(&FormatEtc) == S_OK) { if (pDataObject->GetData(&FormatEtc,&StgMedium) == S_OK) { // Prepare a project file transaction. CProjectManager::CFileTransaction Transaction; HDROP hDrop = (HDROP)GlobalLock(StgMedium.hGlobal); unsigned int uiNumFiles = DragQueryFile(hDrop,0xFFFFFFFF,NULL,NULL); TCHAR szFullName[MAX_PATH]; for (unsigned int i = 0; i < uiNumFiles; i++) { // Add each file to the project. if (DragQueryFile(hDrop,i,szFullName,MAX_PATH - 1)) Transaction.AddFile(szFullName,pTargetNode); } GlobalUnlock(StgMedium.hGlobal); ReleaseStgMedium(&StgMedium); } } else { FormatEtc.cfFormat = static_cast(m_uiClipFormat); if (pDataObject->QueryGetData(&FormatEtc) == S_OK) { if (pDataObject->GetData(&FormatEtc,&StgMedium) == S_OK) { // Prepare a project file transaction. CProjectManager::CFileTransaction Transaction; CProjectDropData *pDropData = (CProjectDropData *)GlobalLock(StgMedium.hGlobal); if (pDropData->m_pParent == NULL) return true; SIZE_T uiNumFiles = (GlobalSize(StgMedium.hGlobal) - sizeof(CProjectDropData)) / sizeof(CItemData *); for (SIZE_T i = 0; i < uiNumFiles; i++) { CItemData *pItemData = pDropData->m_ppData[i]; Transaction.MoveFile(pDropData->m_pParent,pItemData,pTargetNode); } GlobalUnlock(StgMedium.hGlobal); ReleaseStgMedium(&StgMedium); } } } return true; } CProjectTreeViewCtrl::CProjectTreeViewCtrl() { m_pDropTarget = new CProjectTreeViewDropTarget(this); CoLockObjectExternal(m_pDropTarget,TRUE,FALSE); } CProjectTreeViewCtrl::~CProjectTreeViewCtrl() { if (m_pDropTarget != NULL) { CoLockObjectExternal(m_pDropTarget,FALSE,TRUE); m_pDropTarget->Release(); m_pDropTarget = NULL; } } LRESULT CProjectTreeViewCtrl::OnSetFocus(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CProjectNode *pNode = (CProjectNode *)GetSelectedItem().GetData(); g_ProjectManager.TreeSetActive(); g_ProjectManager.NotifyTreeSelChanged(pNode); bHandled = false; return 0; } LRESULT CProjectTreeViewCtrl::OnCustomDraw(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { LPNMTVCUSTOMDRAW lpNMCustomDraw = (LPNMTVCUSTOMDRAW)lParam; switch (lpNMCustomDraw->nmcd.dwDrawStage) { case CDDS_PREPAINT: return CDRF_NOTIFYITEMDRAW; case CDDS_ITEMPREPAINT: CProjectNode *pNode = (CProjectNode *)lpNMCustomDraw->nmcd.lItemlParam; /*if (pNode == NULL || !(pNode->pItemData->ucFlags & PROJECTITEM_FLAG_ISLOCKED)) { bHandled = false; return CDRF_DODEFAULT; } lpNMCustomDraw->clrText = GetSysColor(COLOR_GRAYTEXT); return CDRF_NEWFONT;*/ if (pNode != NULL && pNode->pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) { lpNMCustomDraw->clrText = PROJECTTREEVIEW_COLOR_IMPORTED; return CDRF_NEWFONT; } if (pNode != NULL && pNode->pItemData->ucFlags & PROJECTITEM_FLAG_ISLOCKED) { lpNMCustomDraw->clrText = GetSysColor(COLOR_GRAYTEXT); return CDRF_NEWFONT; } bHandled = false; return CDRF_DODEFAULT; } bHandled = false; return CDRF_DODEFAULT; } void CProjectTreeViewCtrl::BeginDrag(LPNMTREEVIEW pNMTreeView) { if (((CProjectNode *)GetItemData(pNMTreeView->itemNew.hItem))->pItemData->ucFlags & PROJECTITEM_FLAG_ISPROJECTROOT) return; CProjectDropSource *pDropSource = new CProjectDropSource(); CProjectDataObject *pDataObject = new CProjectDataObject(); // Add all file names to the data object. pDataObject->AddFile(((CProjectNode *)GetItemData(pNMTreeView->itemNew.hItem))->pItemData); pDataObject->SetParent((CProjectNode *)GetItemData(GetParentItem(pNMTreeView->itemNew.hItem))); DWORD dwEffect = 0; ::DoDragDrop(pDataObject,pDropSource,DROPEFFECT_MOVE,&dwEffect); pDropSource->Release(); pDataObject->Release(); } void CProjectTreeViewCtrl::ForceRedraw() { RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient,true); } ================================================ FILE: src/app/control/project_tree_view_ctrl.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "ctrl_messages.hh" #include "tree_manager.hh" #include "project_drop_target_base.hh" #define PROJECTTREEVIEW_COLOR_IMPORTED RGB(92,53,102) class CProjectTreeViewDropTarget : public CProjectDropTargetBase { private: CTreeViewCtrlEx *m_pHost; bool HandleDropData(IDataObject *pDataObject,CProjectNode *pTargetNode); public: CProjectTreeViewDropTarget(CTreeViewCtrlEx *pHost); bool OnDragOver(POINTL ptCursor); bool OnDrop(POINTL ptCursor,IDataObject *pDataObject); void OnDragLeave(); }; class CProjectTreeViewCtrl : public CWindowImpl { public: CProjectTreeViewDropTarget *m_pDropTarget; DECLARE_WND_CLASS(_T("ckProjectTreeViewCtrl")); CProjectTreeViewCtrl(); ~CProjectTreeViewCtrl(); BEGIN_MSG_MAP(CProjectTreeViewCtrl) MESSAGE_HANDLER(WM_SETFOCUS,OnSetFocus) MESSAGE_HANDLER(WM_CONTROLCUSTOMDRAW,OnCustomDraw) END_MSG_MAP() LRESULT OnSetFocus(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnCustomDraw(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); void BeginDrag(LPNMTREEVIEW pNMTreeView); void ForceRedraw(); }; ================================================ FILE: src/app/control/shell_list_view_ctrl.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "shell_list_view_ctrl.hh" #include "ctrl_messages.hh" #include "version.hh" unsigned int CF_IDLIST = ::RegisterClipboardFormat(CFSTR_SHELLIDLIST); CShellListViewCtrl::CShellListViewCtrl(HWND hWndParent,HWND hWndReceiver) : m_dwRef(0) { m_hWndParent = hWndParent; m_hWnd = NULL; if (hWndReceiver == NULL) m_hWndReceiver = m_hWndParent; else m_hWndReceiver = hWndReceiver; m_pParentShellFolder = NULL; m_pShellView = NULL; // Used when collecting item data. m_hItemsMem = NULL; m_pidl = NULL; } CShellListViewCtrl::~CShellListViewCtrl() { FreeMemberPointers(); // Make sure that no selection memory is still allocated. if (m_hItemsMem != NULL) EndGetItems(); } HWND CShellListViewCtrl::GetListViewHandle() { if (!m_hWnd) return NULL; // Find the list view control. HWND hWndListView = FindWindowEx(m_hWnd,NULL,WC_LISTVIEW,NULL); if (!::IsWindowVisible(hWndListView)) { hWndListView = FindWindowEx(m_hWnd,NULL,_T("ThumbnailVwExtWnd32"),NULL); hWndListView = FindWindowEx(hWndListView,NULL,WC_LISTVIEW,NULL); } return hWndListView; } void CShellListViewCtrl::FreeMemberPointers() { if (m_pShellView) { m_pShellView->UIActivate(SVUIA_DEACTIVATE); m_pShellView->DestroyViewWindow(); m_pShellView->Release(); } if (m_pParentShellFolder) m_pParentShellFolder->Release(); m_pShellView = NULL; m_pParentShellFolder = NULL; } IShellFolder *CShellListViewCtrl::GetParentShellFolder() { return m_pParentShellFolder; } bool CShellListViewCtrl::IsFolder(LPCITEMIDLIST pidl,IShellFolder *psfParent) { ATLASSERT(NULL != psfParent); if (!psfParent) return false; DWORD dwAttribs = SFGAO_FOLDER | SFGAO_FILESYSTEM | SFGAO_FILESYSANCESTOR | SFGAO_BROWSABLE; HRESULT hResult = psfParent->GetAttributesOf(1,&pidl,&dwAttribs); return ((S_OK == hResult && (dwAttribs & SFGAO_FOLDER) != 0 && ((dwAttribs & SFGAO_FILESYSTEM) != 0 || (dwAttribs & SFGAO_FILESYSANCESTOR) != 0)) && !(dwAttribs & SFGAO_BROWSABLE)); } bool CShellListViewCtrl::IsFolderLink(LPCITEMIDLIST pidl,LPITEMIDLIST *pOutPidl) { ATLASSERT(m_pParentShellFolder); if (!m_pParentShellFolder) return false; // Is pidl a link? DWORD dwAttribs = SFGAO_LINK; m_pParentShellFolder->GetAttributesOf(1,&pidl,&dwAttribs); if (!(dwAttribs & SFGAO_LINK)) return false; // Get the link object. IShellLink *pLink; if (NOERROR != m_pParentShellFolder->GetUIObjectOf(m_hWnd,1,&pidl,IID_IShellLink,0, (void**)&pLink)) { return false; } // Get link target's pidl. LPITEMIDLIST rPidl = NULL,pidlParent = NULL,pidlChild = NULL; if (NOERROR == pLink->GetIDList(&rPidl)) { IShellFolder *psf; if (NOERROR == SHGetDesktopFolder(&psf)) { // If pidl is complex (it probably is), split into parent/child pidls first. if (m_PidlHelp.Split(rPidl,&pidlParent,&pidlChild)) { IShellFolder *psf2; if (NOERROR == psf->BindToObject(pidlParent,NULL,IID_IShellFolder, reinterpret_cast(&psf2))) { if (!IsFolder(pidlChild,psf2)) m_PidlHelp.FreePidl(rPidl); psf2->Release(); } m_PidlHelp.FreePidl(pidlParent); m_PidlHelp.FreePidl(pidlChild); } else if (!IsFolder(rPidl,psf)) { m_PidlHelp.FreePidl(rPidl); } psf->Release(); } } pLink->Release(); if (rPidl) { if (pOutPidl) *pOutPidl = rPidl; else m_PidlHelp.FreePidl(rPidl); return true; } return false; } STDMETHODIMP CShellListViewCtrl::QueryInterface(REFIID iid,void **ppvObject) { if (ppvObject == NULL) return E_POINTER; *ppvObject = NULL; if (iid == IID_IUnknown) *ppvObject = (IUnknown *)(IShellBrowser *)this; else if (iid == IID_IOleWindow) *ppvObject = (IOleWindow *)this; else if (iid == IID_IShellBrowser) *ppvObject = (IShellBrowser *)this; else if (iid == IID_ICommDlgBrowser) *ppvObject = (ICommDlgBrowser *)this; else return E_NOINTERFACE; ((IUnknown *)(*ppvObject))->AddRef(); return S_OK; } STDMETHODIMP_(ULONG) CShellListViewCtrl::AddRef() { return ++m_dwRef; } STDMETHODIMP_(ULONG) CShellListViewCtrl::Release() { return --m_dwRef; } STDMETHODIMP CShellListViewCtrl::ContextSensitiveHelp(BOOL fEnterMode) { return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::GetWindow(HWND *lphwnd) { *lphwnd = m_hWndParent; return S_OK; } STDMETHODIMP CShellListViewCtrl::IncludeObject(THIS_ struct IShellView *ppshv, LPCITEMIDLIST pidl) { // TODO: Implement filtering support. /*if (isISO(pidl)) return S_OK; // Show it. return S_FALSE; // Hide it.*/ return S_OK; } STDMETHODIMP CShellListViewCtrl::OnDefaultCommand(THIS_ struct IShellView *ppshv) { CIDA *pData = BeginGetItems(true); char *pcData = reinterpret_cast(pData) + pData->aoffset[1]; LPCITEMIDLIST pidl = (LPITEMIDLIST)pcData; TCHAR szNewPathName[MAX_PATH]; if (!m_PidlHelp.GetPathName(m_pParentShellFolder,pidl,szNewPathName,MAX_PATH - 1)) return E_FAIL; LPITEMIDLIST pidlTo = NULL; // Check if we're dealing with a folder or a folder link. if (IsFolder(pidl,m_pParentShellFolder)) { // Notify the receiver that a new folder will be opened. ::SendMessage(m_hWndReceiver,WM_SLVC_CHANGEFOLDER,(WPARAM)pidl,(LPARAM)szNewPathName); BrowseObject(pidl,SBSP_SAMEBROWSER | SBSP_RELATIVE); } else if (IsFolderLink(pidl,&pidlTo)) { // Notify the receiver that we will open a shortcut. Shortcuts should be notified // in a different way than regular folders since it will require a deeper search // in the folder tree to find the new path. m_PidlHelp.GetPathName(m_pParentShellFolder,pidlTo,szNewPathName,MAX_PATH - 1); ::SendMessage(m_hWndReceiver,WM_SLVC_CHANGEFOLDERLINK,(WPARAM)pidl,(LPARAM)szNewPathName); BrowseObject(pidlTo,SBSP_SAMEBROWSER | SBSP_ABSOLUTE); } else { if (::SendMessage(m_hWndReceiver,WM_SLVC_FILECOMMAND,(WPARAM)pidl,(LPARAM)szNewPathName) == 1) { if (pidlTo) m_PidlHelp.FreePidl(pidlTo); EndGetItems(); return NOERROR; } EndGetItems(); return E_NOTIMPL; } if (pidlTo) m_PidlHelp.FreePidl(pidlTo); EndGetItems(); return NOERROR; } STDMETHODIMP CShellListViewCtrl::OnStateChange(THIS_ struct IShellView *ppshv,ULONG uChange) { // Handle selection, rename, focus etc. return E_NOTIMPL; } WNDPROC CShellListViewCtrl::m_pOldWndProc = NULL; LRESULT CALLBACK CShellListViewCtrl::WndProc(HWND hWnd,UINT Msg, WPARAM wParam, LPARAM lParam) { //LRESULT lResult = m_pOldWndProc(hWnd,Msg,wParam,lParam); LRESULT lResult = 0; if (::IsWindowUnicode(hWnd)) lResult = ::CallWindowProcW(m_pOldWndProc,hWnd,Msg,wParam,lParam); else lResult = ::CallWindowProcA(m_pOldWndProc,hWnd,Msg,wParam,lParam); // We need to redirect this message to the parent so later on the splitter // that hosts this control will know that we have activated this window. // Otherwise the splitter will not know that it should return the focus to // this window if the focus is stolen by for example the menu. if (Msg == WM_MOUSEACTIVATE) ::SendMessage(GetParent(hWnd),Msg,wParam,lParam); return lResult; } STDMETHODIMP CShellListViewCtrl::BrowseObject(LPCITEMIDLIST pidl,UINT wFlags) { if (wFlags & SBSP_PARENT && !m_pidl) return E_FAIL; if (wFlags & SBSP_RELATIVE && !m_pParentShellFolder) return E_FAIL; IShellFolder *pShellFolder = m_pParentShellFolder; LPITEMIDLIST pidlCopy = NULL; HRESULT hr = E_FAIL; // Get IShellFolder, FULLY QUALIFIED pidl. Check if we are dealing with the desktop. if (pidl == NULL && !(wFlags & SBSP_PARENT)) { FreeMemberPointers(); if (SUCCEEDED(SHGetDesktopFolder(&m_pParentShellFolder))) hr = SHGetSpecialFolderLocation(m_hWndParent,CSIDL_DESKTOP,&pidlCopy); } else { if (wFlags & SBSP_RELATIVE) { // Browse child folder pidlCopy = ILCombine(m_pidl,pidl); hr = pShellFolder->BindToObject(pidl,NULL,IID_IShellFolder, reinterpret_cast(&m_pParentShellFolder)); } else { if (wFlags & SBSP_PARENT) { // Browse parent: pidlCopy = parent folder's PIDL. if (!m_PidlHelp.Split(m_pidl,&pidlCopy,NULL)) return E_FAIL; } else { // Browse absolute PIDL: pidlCopy = clone(pidl). pidlCopy = ILClone(pidl); } // Create IShellFolder for target PIDL through Desktop folder. IShellFolder *pShellFolder2; if (SUCCEEDED(hr = SHGetDesktopFolder(&pShellFolder2))) { if (SUCCEEDED(pShellFolder2->BindToObject(pidlCopy,NULL, IID_IShellFolder, reinterpret_cast(&m_pParentShellFolder)))) { pShellFolder2->Release(); } else { m_pParentShellFolder = pShellFolder2; } } } } if (FAILED(hr)) { if (pidlCopy) m_PidlHelp.FreePidl(pidlCopy); if (m_pParentShellFolder) m_pParentShellFolder->Release(); m_pParentShellFolder = pShellFolder; return hr; } ATLASSERT(m_pParentShellFolder && pidlCopy); if (!m_pParentShellFolder || !pidlCopy) return E_FAIL; // Use the IShellFolder to create a view window FOLDERSETTINGS fs = { FVM_DETAILS,FWF_SNAPTOGRID/* | FWF_NOICONS*/ }; if (m_pShellView) m_pShellView->GetCurrentInfo(&fs); IShellView *pShellView = m_pShellView; m_pShellView = NULL; HWND hWndShellView = NULL; if (SUCCEEDED(hr = m_pParentShellFolder->CreateViewObject(m_hWndParent,IID_IShellView, reinterpret_cast(&m_pShellView)))) { hr = m_pShellView->CreateViewWindow(pShellView,&fs, static_cast(this),&CWindow::rcDefault,&hWndShellView); } if (FAILED(hr)) { if (m_pShellView) { m_pShellView->UIActivate(SVUIA_DEACTIVATE); m_pShellView->DestroyViewWindow(); m_pShellView->Release(); m_pShellView = pShellView; } m_PidlHelp.FreePidl(pidlCopy); m_pParentShellFolder->Release(); m_pParentShellFolder = pShellFolder; return hr; } // Restore the original windows procedure to the old window. if (::IsWindow(m_hWnd) && m_pOldWndProc != NULL) { //::SetWindowLongPtr(m_hWnd,GWLP_WNDPROC,(LONG_PTR)m_pOldWndProc); if (::IsWindowUnicode(m_hWnd)) ::SetWindowLongPtrW(m_hWnd,GWLP_WNDPROC,(LONG_PTR)m_pOldWndProc); else ::SetWindowLongPtrA(m_hWnd,GWLP_WNDPROC,(LONG_PTR)m_pOldWndProc); } m_hWnd = hWndShellView; // Update the window to use our modified procedure. //m_pOldWndProc = (WNDPROC)::GetWindowLongPtr(m_hWnd,GWLP_WNDPROC); //::SetWindowLongPtr(m_hWnd,GWLP_WNDPROC,(LONG_PTR)WndProc); if (::IsWindowUnicode(m_hWnd)) { m_pOldWndProc = (WNDPROC)::GetWindowLongPtrW(m_hWnd,GWLP_WNDPROC); ::SetWindowLongPtrW(m_hWnd,GWLP_WNDPROC,(LONG_PTR)WndProc); } else { m_pOldWndProc = (WNDPROC)::GetWindowLongPtrA(m_hWnd,GWLP_WNDPROC); ::SetWindowLongPtrA(m_hWnd,GWLP_WNDPROC,(LONG_PTR)WndProc); } if (m_pidl) m_PidlHelp.FreePidl(m_pidl); m_pidl = pidlCopy; if (pShellView != NULL) { pShellView->UIActivate(SVUIA_DEACTIVATE); pShellView->DestroyViewWindow(); pShellView->Release(); } if (pShellFolder) pShellFolder->Release(); // Only set the focus to the new list view if the old shell list view instance // had the focus. bool bSetFocus = ::GetFocus() == GetListViewHandle(); // Notify the receiver. ::SendMessage(m_hWndReceiver,WM_SLVC_BROWSEOBJECT,0,(LPARAM)m_hWnd); m_pShellView->UIActivate(bSetFocus ? SVUIA_ACTIVATE_FOCUS : SVUIA_ACTIVATE_NOFOCUS); // Select first item in list view. HWND hWndListView = FindWindowEx(m_hWnd,NULL,WC_LISTVIEW,NULL); ListView_SetItemState(hWndListView,0,LVIS_FOCUSED | LVIS_SELECTED,0x000F); ::ShowWindow(hWndListView,SW_NORMAL); // Update the combobox. ::SendMessage(m_hWndReceiver,WM_SLVC_DONEBROWSEOBJECT,0,(LPARAM)m_hWnd); // Subclass the internal list view. // UPDATE: Causes the list view to turn white when double-clicking on a // folder in the explorer view. /*if (hWndListView != NULL) { if (m_InternalListView.m_hWnd != NULL) { m_InternalListView.UnsubclassWindow(); } m_InternalListView.SubclassWindow(hWndListView); m_InternalListView.SetHost(m_pShellView); // Force the WS_EX_CLIENTEDGE style on Windows Vista (which disables it by default). if (g_WinVer.m_ulMajorVersion == MAJOR_WINVISTA) m_InternalListView.ModifyStyleEx(0,WS_EX_CLIENTEDGE,SWP_FRAMECHANGED); }*/ if (hWndListView != NULL) { // Force the WS_EX_CLIENTEDGE style on Windows Vista (which disables it by default). if (g_WinVer.m_ulMajorVersion == MAJOR_WINVISTA) { unsigned long ulStyle = ::GetWindowLong(hWndListView,GWL_EXSTYLE); ::SetWindowLong(hWndListView,GWL_EXSTYLE,ulStyle | WS_EX_CLIENTEDGE); ::SetWindowPos(hWndListView,NULL,0,0,0,0,SWP_NOSIZE | SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE | SWP_FRAMECHANGED); } } return NOERROR; } STDMETHODIMP CShellListViewCtrl::EnableModelessSB(BOOL fEnable) { return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::GetControlWindow(UINT id,HWND *lphwnd) { if (lphwnd == NULL) return E_POINTER; /*if (FCW_STATUS == id) { *lphwnd = m_hWndStatusBar; return S_OK; }*/ return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::GetViewStateStream(DWORD grfMode,LPSTREAM *ppStrm) { return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::InsertMenusSB(HMENU hmenuShared, LPOLEMENUGROUPWIDTHS lpMenuWidths) { return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::OnViewWindowActive(struct IShellView *ppshv) { return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::QueryActiveShellView(struct IShellView **ppshv) { m_pShellView->AddRef(); *ppshv = m_pShellView; return S_OK; } STDMETHODIMP CShellListViewCtrl::RemoveMenusSB(HMENU hmenuShared) { return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::SendControlMsg(UINT id,UINT uMsg,WPARAM wParam, LPARAM lParam,LRESULT *pret) { if(pret == NULL) return E_POINTER; /*if (FCW_STATUS == id) { *pret = ::SendMessage(m_hWndStatusBar,uMsg,wParam,lParam); return S_OK; }*/ return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::SetMenuSB(HMENU hmenuShared,HOLEMENU holemenuReserved,HWND hwndActiveObject) { return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::SetStatusTextSB(LPCOLESTR lpszStatusText) { return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::SetToolbarItems(LPTBBUTTON lpButtons,UINT nButtons,UINT uFlags) { return E_NOTIMPL; } STDMETHODIMP CShellListViewCtrl::TranslateAcceleratorSB(LPMSG lpmsg,WORD wID) { return S_OK; } bool CShellListViewCtrl::IsAtTop() { return m_pidl->mkid.cb < 1; } CIDA *CShellListViewCtrl::BeginGetItems(bool bSelected) { if (m_hItemsMem != NULL) EndGetItems(); IDataObject *pSelection; HRESULT hResult = m_pShellView->GetItemObject(bSelected ? SVGIO_SELECTION : SVGIO_ALLVIEW, IID_IDataObject,(void **)&pSelection); if (!SUCCEEDED(hResult)) return NULL; // CFSTR_SHELLIDLIST FORMATETC fetc; fetc.cfFormat = static_cast(CF_IDLIST); fetc.dwAspect = DVASPECT_CONTENT; fetc.ptd = NULL; fetc.lindex = -1; fetc.tymed = TYMED_HGLOBAL; hResult = pSelection->QueryGetData(&fetc); if (!SUCCEEDED(hResult)) return NULL; STGMEDIUM stm; hResult = pSelection->GetData(&fetc,&stm); if (!SUCCEEDED(hResult)) return NULL; CIDA *pData = (CIDA *)GlobalLock(stm.hGlobal); if (pData == NULL) return NULL; if (pData == NULL || pData->cidl < 1) return NULL; return pData; } void CShellListViewCtrl::EndGetItems() { GlobalUnlock(m_hItemsMem); m_hItemsMem = NULL; } ================================================ FILE: src/app/control/shell_list_view_ctrl.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "pidl_helper.hh" class CShellListViewCtrl : public IShellBrowser, public ICommDlgBrowser { private: // Internal list view class used for translating the default shell hot keys. /*class CInternalListViewCtrl : public CWindowImpl, public CMessageFilter { private: IShellView *m_pHostShellView; bool m_bRegistered; public: BEGIN_MSG_MAP(CInternalListViewCtrl) MESSAGE_HANDLER(WM_SETFOCUS,OnShowWindow) END_MSG_MAP() CInternalListViewCtrl() { m_bRegistered = false; } virtual BOOL PreTranslateMessage(MSG *pMsg) { if (GetFocus() == m_hWnd) { if (pMsg->message >= WM_KEYFIRST && pMsg->message <= WM_KEYLAST) { if (m_pHostShellView->TranslateAccelerator(pMsg) == S_OK) return TRUE; } } return FALSE; } LRESULT OnKeyDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (uMsg >= WM_KEYFIRST && uMsg <= WM_KEYLAST) { MSG Msg; Msg.message = uMsg; Msg.wParam = wParam; Msg.lParam = lParam; if (m_pHostShellView->TranslateAccelerator(&Msg) == S_OK) { bHandled = true; return TRUE; } } bHandled = false; return 0; } LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (!m_bRegistered) { AddToMessageLoop(); m_bRegistered = true; } bHandled = false; return 0; } void SetHost(IShellView *pHostShellView) { m_pHostShellView = pHostShellView; } void AddToMessageLoop() { CMessageLoop *pLoop = _Module.GetMessageLoop(); pLoop->AddMessageFilter(this); } void RemoveFromMessageLoop() { CMessageLoop *pLoop = _Module.GetMessageLoop(); pLoop->RemoveMessageFilter(this); } }; CInternalListViewCtrl m_InternalListView;*/ static WNDPROC m_pOldWndProc; static LRESULT CALLBACK WndProc(HWND hwnd,UINT message,WPARAM wParam, LPARAM lParam); DWORD m_dwRef; HWND m_hWndParent; HWND m_hWndReceiver; HWND m_hWnd; IShellFolder *m_pParentShellFolder; IShellView *m_pShellView; HGLOBAL m_hItemsMem; CPidlHelper m_PidlHelp; LPITEMIDLIST m_pidl; void FreeMemberPointers(); bool IsFolder(LPCITEMIDLIST pidl,IShellFolder *psfParent); bool IsFolderLink(LPCITEMIDLIST pidl,LPITEMIDLIST *pOutPidl); //HWND GetListViewHandle(); public: CShellListViewCtrl(HWND hWndParent,HWND hWndReceiver = NULL); ~CShellListViewCtrl(); HWND GetListViewHandle(); // IUnknown members. STDMETHOD(QueryInterface)(REFIID iid,void **ppvObject); STDMETHOD_(ULONG,AddRef)(); STDMETHOD_(ULONG,Release)(); // IOleWindow members. STDMETHOD(ContextSensitiveHelp)(BOOL fEnterMode); STDMETHOD(GetWindow)(HWND *lphwnd); // ICommDlgBrowser members. STDMETHOD(IncludeObject)(THIS_ struct IShellView *ppshv,LPCITEMIDLIST pidl); STDMETHOD(OnDefaultCommand)(THIS_ struct IShellView *ppshv); STDMETHOD(OnStateChange)(THIS_ struct IShellView *ppshv,ULONG uChange); // IShellBrowser members (same as IOleInPlaceFrame). STDMETHOD(BrowseObject)(LPCITEMIDLIST pidl,UINT wFlags); STDMETHOD(EnableModelessSB)(BOOL fEnable); STDMETHOD(GetControlWindow)(UINT id,HWND *lphwnd); STDMETHOD(GetViewStateStream)(DWORD grfMode,LPSTREAM *ppStrm); STDMETHOD(InsertMenusSB)(HMENU hmenuShared,LPOLEMENUGROUPWIDTHS lpMenuWidths); STDMETHOD(OnViewWindowActive)(struct IShellView *ppshv); STDMETHOD(QueryActiveShellView)(struct IShellView **ppshv); STDMETHOD(RemoveMenusSB)(HMENU hmenuShared); STDMETHOD(SendControlMsg)(UINT id,UINT uMsg,WPARAM wParam,LPARAM lParam,LRESULT *pret); STDMETHOD(SetMenuSB)(HMENU hmenuShared,HOLEMENU holemenuReserved,HWND hwndActiveObject); STDMETHOD(SetStatusTextSB)(LPCOLESTR lpszStatusText); STDMETHOD(SetToolbarItems)(LPTBBUTTON lpButtons,UINT nButtons,UINT uFlags); STDMETHOD(TranslateAcceleratorSB)(LPMSG lpmsg,WORD wID); // Miscellaneous. IShellFolder *GetParentShellFolder(); bool IsAtTop(); CIDA *BeginGetItems(bool bSelected); void EndGetItems(); // Operators. operator HWND () { return m_hWnd; } }; ================================================ FILE: src/app/control/space_meter.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "string_table.hh" #include "lang_util.hh" #include "version.hh" #include "space_meter.hh" CSpaceMeter::CSpaceMeter() : m_bIsUpdatePending( false ) { m_iMeterPosition = 0; m_iMeterSegmentSpacing = 0; m_hProgressTheme = NULL; m_iHorIndent = SPACEMETER_BARINDENT_THEMED; // By default we use the size display mode. m_iDisplayMode = SPACEMETER_DMSIZE; // The default draw state is ofcourse normal. m_iDrawState = SPACEMETER_DRAWSTATE_NORMAL; m_uiAllocatedSize = 1; m_uiDiscSize = 1; m_uiMeterSize = 1; for (unsigned int i = 0; i < SPACEMETER_METER_COUNT; i++) lstrcpy(m_uiMeterSegments[i],_T("0 B")); m_hBarBorderBrush = ::CreateSolidBrush(SPACEMETER_BORDERCOLOR); m_hWarnBarBorderBrush = ::CreateSolidBrush(SPACEMETER_WARNBORDERCOLOR); m_hFullBarBorderBrush = ::CreateSolidBrush(SPACEMETER_FULLBORDERCOLOR); m_ToolTipText.reserve(256); // Create and fill the popup menu. m_hPopupMenu = CreatePopupMenu(); FillPopupMenu(); } CSpaceMeter::~CSpaceMeter() { ::DeleteObject(m_hBarBorderBrush); ::DeleteObject(m_hWarnBarBorderBrush); ::DeleteObject(m_hFullBarBorderBrush); // Destroy the popup menu. if (m_hPopupMenu != NULL) DestroyMenu(m_hPopupMenu); // Destroy the tooltip control. if (m_ToolTip.IsWindow()) m_ToolTip.DestroyWindow(); // Close the progress theme data. if (m_hProgressTheme != NULL) g_VisualStyles.CloseThemeData(m_hProgressTheme); } void CSpaceMeter::FillPopupMenu() { // Remove the old items. int iMenuItemCount = GetMenuItemCount(m_hPopupMenu); for (int i = iMenuItemCount - 1; i >= 0; i--) RemoveMenu(m_hPopupMenu,i,MF_BYPOSITION); // Add new items (and on the same time convert them to radio items). unsigned int uiMenuIndex = 0; unsigned int uiCommand = SPACEMETER_POPUPMENU_IDBASE; CMenuItemInfo mii; mii.fMask = 0x100; mii.fType = MFT_RADIOCHECK; InsertMenu(m_hPopupMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiCommand++,_T("DVD 7.96 GiB")); SetMenuItemInfo(m_hPopupMenu,uiMenuIndex,TRUE,&mii); uiMenuIndex++; InsertMenu(m_hPopupMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiCommand++,_T("DVD 4.38 GiB")); SetMenuItemInfo(m_hPopupMenu,uiMenuIndex,TRUE,&mii); uiMenuIndex++; InsertMenu(m_hPopupMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiCommand++,_T("99 min (870 MiB)")); SetMenuItemInfo(m_hPopupMenu,uiMenuIndex,TRUE,&mii); uiMenuIndex++; InsertMenu(m_hPopupMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiCommand++,_T("90 min (791 MiB)")); SetMenuItemInfo(m_hPopupMenu,uiMenuIndex,TRUE,&mii); uiMenuIndex++; InsertMenu(m_hPopupMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiCommand++,_T("80 min (703 MiB)")); SetMenuItemInfo(m_hPopupMenu,uiMenuIndex,TRUE,&mii); uiMenuIndex++; InsertMenu(m_hPopupMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiCommand++,_T("74 min (650 MiB)")); SetMenuItemInfo(m_hPopupMenu,uiMenuIndex,TRUE,&mii); uiMenuIndex++; InsertMenu(m_hPopupMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiCommand++,_T("24 min (210 MiB)")); SetMenuItemInfo(m_hPopupMenu,uiMenuIndex,TRUE,&mii); uiMenuIndex++; InsertMenu(m_hPopupMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiCommand++,_T("21 min (185 MiB)")); SetMenuItemInfo(m_hPopupMenu,uiMenuIndex,TRUE,&mii); uiMenuIndex++; } void CSpaceMeter::DrawBar(HDC hDC,RECT *pClientRect) { int iBottom = pClientRect->bottom - SPACEMETER_BARINDENT_BOTTOM; RECT rcBar = { pClientRect->left + m_iHorIndent, iBottom - SPACEMETER_BAR_HEIGHT, pClientRect->right - m_iHorIndent, iBottom }; // Draw the meter. DrawMeter(hDC,pClientRect,&rcBar); // Draw a different meter on Windows Vista systems. if (m_hProgressTheme == NULL) { switch (m_iDrawState) { case SPACEMETER_DRAWSTATE_NORMAL: FillRect(hDC,&rcBar,m_hBarBorderBrush); break; case SPACEMETER_DRAWSTATE_WARN: FillRect(hDC,&rcBar,m_hWarnBarBorderBrush); break; case SPACEMETER_DRAWSTATE_FULL: FillRect(hDC,&rcBar,m_hFullBarBorderBrush); break; } ContractRect(&rcBar,1); // First we draw the free space. rcBar.left += m_iMeterPosition; switch (m_iDrawState) { case SPACEMETER_DRAWSTATE_NORMAL: DrawVertGradientRect(hDC,&rcBar,SPACEMETER_BARCOLOR_FREETOP,SPACEMETER_BARCOLOR_FREEBOTTOM); break; case SPACEMETER_DRAWSTATE_WARN: DrawVertGradientRect(hDC,&rcBar,SPACEMETER_WARNBARCOLOR_FREETOP,SPACEMETER_WARNBARCOLOR_FREEBOTTOM); break; case SPACEMETER_DRAWSTATE_FULL: DrawVertGradientRect(hDC,&rcBar,SPACEMETER_FULLBARCOLOR_FREETOP,SPACEMETER_FULLBARCOLOR_FREEBOTTOM); break; } // Next we draw the allocated space. rcBar.left -= m_iMeterPosition; rcBar.right = m_iMeterPosition + m_iHorIndent + 1; switch (m_iDrawState) { case SPACEMETER_DRAWSTATE_NORMAL: DrawVertGradientRect(hDC,&rcBar,SPACEMETER_BARCOLOR_TOP,SPACEMETER_BARCOLOR_BOTTOM); break; case SPACEMETER_DRAWSTATE_WARN: DrawVertGradientRect(hDC,&rcBar,SPACEMETER_WARNBARCOLOR_TOP,SPACEMETER_WARNBARCOLOR_BOTTOM); break; case SPACEMETER_DRAWSTATE_FULL: DrawVertGradientRect(hDC,&rcBar,SPACEMETER_FULLBARCOLOR_TOP,SPACEMETER_FULLBARCOLOR_BOTTOM); break; } } else { g_VisualStyles.DrawThemeBackground(m_hProgressTheme,hDC,11,2,&rcBar,NULL); // Draw the allocated space. //rcBar.left++; rcBar.right = m_iMeterPosition + m_iHorIndent + 1; switch (m_iDrawState) { case SPACEMETER_DRAWSTATE_NORMAL: g_VisualStyles.DrawThemeBackground(m_hProgressTheme,hDC,5,4,&rcBar,NULL); break; case SPACEMETER_DRAWSTATE_WARN: g_VisualStyles.DrawThemeBackground(m_hProgressTheme,hDC,5,3,&rcBar,NULL); break; case SPACEMETER_DRAWSTATE_FULL: g_VisualStyles.DrawThemeBackground(m_hProgressTheme,hDC,5,2,&rcBar,NULL); break; } } } void CSpaceMeter::DrawFullBar(HDC hDC,RECT *pClientRect) { int iBottom = pClientRect->bottom - SPACEMETER_BARINDENT_BOTTOM; RECT rcBar = { pClientRect->left + m_iHorIndent, iBottom - SPACEMETER_BAR_HEIGHT, pClientRect->right - m_iHorIndent, iBottom }; // Draw the meter. DrawMeter(hDC,pClientRect,&rcBar); // Draw a different meter on Windows Vista systems. if (m_hProgressTheme == NULL) { FillRect(hDC,&rcBar,m_hFullBarBorderBrush); ContractRect(&rcBar,1); // Draw the allocated space. DrawVertGradientRect(hDC,&rcBar,SPACEMETER_FULLBARCOLOR_TOP,SPACEMETER_FULLBARCOLOR_BOTTOM); } else { g_VisualStyles.DrawThemeBackground(m_hProgressTheme,hDC,11,2,&rcBar,NULL); // Draw the allocated space. g_VisualStyles.DrawThemeBackground(m_hProgressTheme,hDC,5,2,&rcBar,NULL); } } void CSpaceMeter::DrawMeter(HDC hDC,RECT *pClientRect,RECT *pBarRect) { int iLineTop = pBarRect->bottom + SPACEMETER_METER_SPACING; RECT rcLine = { 0, iLineTop, 0, iLineTop + SPACEMETER_METER_HEIGHT }; RECT rcText = { 0, iLineTop, pBarRect->right, pClientRect->bottom }; HFONT hOldFont = (HFONT)SelectObject(hDC,AtlGetDefaultGuiFont()); for (unsigned int i = 0; i < SPACEMETER_METER_COUNT; i++) { // Draw the line. rcLine.left = pBarRect->left + i * m_iMeterSegmentSpacing; rcLine.right = rcLine.left + 1; ::FillRect(hDC,&rcLine,::GetSysColorBrush(COLOR_WINDOWTEXT)); // Draw the text. ::SetBkMode(hDC,TRANSPARENT); ::SetTextColor(hDC,::GetSysColor(COLOR_WINDOWTEXT)); rcText.left = rcLine.left + SPACEMETER_METERTEXT_INDENT_LEFT; DrawText(hDC,m_uiMeterSegments[i],lstrlen(m_uiMeterSegments[i]),&rcText, DT_LEFT | DT_END_ELLIPSIS | DT_SINGLELINE); } SelectObject(hDC,hOldFont); } void CSpaceMeter::UpdateMeter(int iClientWidth) { int iMeterWidth = iClientWidth - m_iHorIndent - m_iHorIndent - 2; m_iMeterSegmentSpacing = iMeterWidth / SPACEMETER_METER_COUNT; unsigned __int64 uiAllocatedSize = min(m_uiAllocatedSize,m_uiMeterSize); m_iMeterPosition = (int)(((float)uiAllocatedSize / m_uiMeterSize) * iMeterWidth); } void CSpaceMeter::UpdateToolTip() { TCHAR szBuffer[ 200 ]; // Must be bigger than szFormattedInt, see below. const TCHAR *szUsed = lngGetString(SPACEMETER_USED); const TCHAR *szFree = lngGetString(SPACEMETER_FREE); unsigned __int64 uiFree = m_uiAllocatedSize > m_uiDiscSize ? 0 : m_uiDiscSize - m_uiAllocatedSize; if (m_iDisplayMode == SPACEMETER_DMSIZE) { TCHAR szFormattedInt[ 160 ]; // Used. m_ToolTipText = szUsed; FormatBytes(szBuffer,m_uiAllocatedSize); m_ToolTipText += szBuffer; FormatInteger( m_uiAllocatedSize, szFormattedInt, _countof( szFormattedInt ) ); lsnprintf_s(szBuffer,64,_T(" (%s Bytes)\r\n"),szFormattedInt); m_ToolTipText += szBuffer; // Free. m_ToolTipText += szFree; FormatBytes(szBuffer,uiFree); m_ToolTipText += szBuffer; FormatInteger( uiFree, szFormattedInt, _countof( szFormattedInt ) ); lsnprintf_s(szBuffer,64,_T(" (%s Bytes)"),szFormattedInt); m_ToolTipText += szBuffer; } else { // Used. m_ToolTipText = szUsed; lsnprintf_s(szBuffer,64,lngGetString(MISC_MINUTES),m_uiAllocatedSize/(1000 * 60)); m_ToolTipText += szBuffer; m_ToolTipText += _T("\r\n"); // Free. m_ToolTipText += szFree; lsnprintf_s(szBuffer,64,lngGetString(MISC_MINUTES),uiFree/(1000 * 60)); m_ToolTipText += szBuffer; } } void CSpaceMeter::SetDiscSize(unsigned int uiDiscSize) { for (unsigned int i = 0; i < SPACEMETER_POPUPMENU_COUNT; i++) ::CheckMenuItem(m_hPopupMenu,i,MF_BYPOSITION | MF_UNCHECKED); switch (uiDiscSize) { case SPACEMETER_SIZE_DLDVD: m_uiDiscSize = 8547991552; ::CheckMenuItem(m_hPopupMenu,0,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_DVD: m_uiDiscSize = 4702989189; ::CheckMenuItem(m_hPopupMenu,1,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_870MB: m_uiDiscSize = 912261120; ::CheckMenuItem(m_hPopupMenu,2,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_791MB: m_uiDiscSize = 829423616; ::CheckMenuItem(m_hPopupMenu,3,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_703MB: m_uiDiscSize = 737148928; ::CheckMenuItem(m_hPopupMenu,4,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_650MB: m_uiDiscSize = 681574400; ::CheckMenuItem(m_hPopupMenu,5,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_210MB: m_uiDiscSize = 220200960; ::CheckMenuItem(m_hPopupMenu,6,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_185MB: m_uiDiscSize = 193986560; ::CheckMenuItem(m_hPopupMenu,7,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_1020MIN: // This is incorrect, I have not been able to find how many sectors a dual layer DVD can contain. m_uiDiscSize = 1020 * 1000 * 60; ::CheckMenuItem(m_hPopupMenu,0,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_510MIN: m_uiDiscSize = 510 * 1000 * 60; ::CheckMenuItem(m_hPopupMenu,1,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_99MIN: m_uiDiscSize = 99 * 1000 * 60; ::CheckMenuItem(m_hPopupMenu,2,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_90MIN: m_uiDiscSize = 90 * 1000 * 60; ::CheckMenuItem(m_hPopupMenu,3,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_80MIN: m_uiDiscSize = 80 * 1000 * 60; ::CheckMenuItem(m_hPopupMenu,4,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_74MIN: m_uiDiscSize = 74 * 1000 * 60; ::CheckMenuItem(m_hPopupMenu,5,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_24MIN: m_uiDiscSize = 24 * 1000 * 60; ::CheckMenuItem(m_hPopupMenu,6,MF_BYPOSITION | MF_CHECKED); break; case SPACEMETER_SIZE_21MIN: m_uiDiscSize = 21 * 1000 * 60; ::CheckMenuItem(m_hPopupMenu,7,MF_BYPOSITION | MF_CHECKED); break; } unsigned __int64 uiSegmentSize = m_uiDiscSize / (SPACEMETER_METER_COUNT - 1); unsigned __int64 uiCurSegment = 0; if (m_iDisplayMode == SPACEMETER_DMSIZE) { for (unsigned int i = 0; i < SPACEMETER_METER_COUNT; i++) { // For segments larger than 1GB we allow two decimals (by using the standard FormatBytes function). if (m_uiMeterSegments[i],uiCurSegment > 1024 * 1024 * 1024) FormatBytes(m_uiMeterSegments[i],uiCurSegment); else FormatBytesEx(m_uiMeterSegments[i],uiCurSegment); uiCurSegment += uiSegmentSize; } } else { for (unsigned int i = 0; i < SPACEMETER_METER_COUNT; i++) { // Minutes. lsnprintf_s(m_uiMeterSegments[i],SPACEMETER_METERTEXT_SIZE,_T("%d min"),uiCurSegment/(1000 * 60)); uiCurSegment += uiSegmentSize; } } // The meter hold the disc size + one segment. m_uiMeterSize = m_uiDiscSize + uiSegmentSize; } void CSpaceMeter::SetAllocatedSize(unsigned __int64 uiAllocatedSize) { m_uiAllocatedSize = uiAllocatedSize; RequestDelayedUpdate(); } void CSpaceMeter::IncreaseAllocatedSize(unsigned __int64 uiSize) { SetAllocatedSize(m_uiAllocatedSize + uiSize); } void CSpaceMeter::DecreaseAllocatedSize(unsigned __int64 uiSize) { SetAllocatedSize(m_uiAllocatedSize - uiSize); } void CSpaceMeter::RequestDelayedUpdate() { if ( m_bIsUpdatePending ) return; ATLVERIFY( 0 != PostMessage( WMU_SPACE_METER_DELAYED_UPDATE, 0, 0 ) ); m_bIsUpdatePending = true; } LRESULT CSpaceMeter::OnDelayedUpdate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { ATLASSERT( uMsg == WMU_SPACE_METER_DELAYED_UPDATE ); ATLASSERT( wParam == 0 ); ATLASSERT( lParam == 0 ); m_bIsUpdatePending = false; if (m_uiAllocatedSize > m_uiMeterSize) m_iDrawState = SPACEMETER_DRAWSTATE_OUTOFSCOPE; else if (m_uiAllocatedSize > m_uiDiscSize) { unsigned __int64 uiOverBurnAmount = m_iDisplayMode == SPACEMETER_DMSIZE ? SPACEMETER_OVERBURNSIZE : SPACEMETER_OVERBURNLENGTH; if (m_uiAllocatedSize < m_uiDiscSize + uiOverBurnAmount) m_iDrawState = SPACEMETER_DRAWSTATE_WARN; else m_iDrawState = SPACEMETER_DRAWSTATE_FULL; } else { m_iDrawState = SPACEMETER_DRAWSTATE_NORMAL; } // Update the meter. RECT rcClient; GetClientRect(&rcClient); UpdateMeter(rcClient.right); // Finally update the tooltip text buffer. UpdateToolTip(); // Trigger a repaint. RECT rcSpaceMeter; GetClientRect(&rcSpaceMeter); InvalidateRect(&rcSpaceMeter,true); bHandled = true; return 0; // Return value unused. } unsigned __int64 CSpaceMeter::GetAllocatedSize() { return m_uiAllocatedSize; } void CSpaceMeter::SetDisplayMode(int iDisplayMode) { m_iDisplayMode = iDisplayMode; } void CSpaceMeter::Initialize() { // Create the tool tip. m_ToolTip.Create(m_hWnd); m_ToolTip.SetMaxTipWidth(200); CToolInfo ti(0,m_hWnd,SPACEMETER_TOOLTIP_ID,NULL,LPSTR_TEXTCALLBACK); m_ToolTip.AddTool(&ti); m_ToolTip.Activate(true); // Initialize the progress theme data. if (g_WinVer.m_ulMajorVersion == MAJOR_WINVISTA && g_WinVer.m_ulMinorVersion == MINOR_WINVISTA) { m_hProgressTheme = g_VisualStyles.OpenThemeData(m_hWnd,L"PROGRESS"); } } LRESULT CSpaceMeter::OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // If the application is themed, we use a different horizontal indentation. if (!g_VisualStyles.IsThemeActive()) m_iHorIndent = SPACEMETER_BARINDENT_NORMAL; return 0; } LRESULT CSpaceMeter::OnSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { LRESULT lResult = DefWindowProc(uMsg,wParam,lParam); unsigned int uiWidth = LOWORD(lParam); UpdateMeter(uiWidth); // Update the tooltip region. if (m_ToolTip.IsWindow()) { RECT rcClient = { 0,0,uiWidth,HIWORD(lParam) }; m_ToolTip.SetToolRect(m_hWnd,SPACEMETER_TOOLTIP_ID,&rcClient); } return lResult; } LRESULT CSpaceMeter::OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CPaintDC dc(m_hWnd); RECT rcClient; GetClientRect(&rcClient); HDC hMemDC; HBITMAP hMemBitmap; hMemDC = CreateCompatibleDC(dc); hMemBitmap = CreateCompatibleBitmap(dc,rcClient.right,rcClient.bottom); HBITMAP hOldBitmap = (HBITMAP)SelectObject(hMemDC,hMemBitmap); // Draw the background. FillRect(hMemDC,&rcClient,GetSysColorBrush(COLOR_BTNFACE)); // Draw the bar. if (m_iDrawState == SPACEMETER_DRAWSTATE_OUTOFSCOPE) DrawFullBar(hMemDC,&rcClient); // Just a faster draw method. else DrawBar(hMemDC,&rcClient); BitBlt(dc,0,0,rcClient.right,rcClient.bottom,hMemDC,0,0,SRCCOPY); SelectObject(hMemDC,hOldBitmap); ReleaseDC(dc); DeleteDC(hMemDC); DeleteObject(hMemBitmap); return 0; } LRESULT CSpaceMeter::OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { return true; } LRESULT CSpaceMeter::OnRButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { POINT CursorPos; GetCursorPos(&CursorPos); TrackPopupMenuEx(m_hPopupMenu,0,CursorPos.x,CursorPos.y,m_hWnd,NULL); bHandled = false; return 0; } LRESULT CSpaceMeter::OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (m_ToolTip.IsWindow()) { MSG Msg = { m_hWnd,uMsg,wParam,lParam }; m_ToolTip.RelayEvent(&Msg); } bHandled = false; return 0; } LRESULT CSpaceMeter::OnGetDispInfo(int idCtrl,LPNMHDR pnmh,BOOL &bHandled) { // Make sure that the notification is about the control we care about. if (pnmh->hwndFrom != m_ToolTip) { bHandled = FALSE; return 0; } LPNMTTDISPINFO pNMTDI = (LPNMTTDISPINFO)pnmh; pNMTDI->lpszText = const_cast(m_ToolTipText.c_str()); return 0; } LRESULT CSpaceMeter::OnPopupMenuClick(UINT uNotifyCode,int nID,CWindow wnd) { nID -= SPACEMETER_POPUPMENU_IDBASE; if (m_iDisplayMode == SPACEMETER_DMSIZE) SetDiscSize(nID); else SetDiscSize(nID + SPACEMETER_POPUPMENU_COUNT); SetAllocatedSize(m_uiAllocatedSize); return 0; } ================================================ FILE: src/app/control/space_meter.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include // COMMAND_RANGE_HANDLER_EX #include "visual_styles.hh" #include "ctrl_messages.hh" #define SPACEMETER_BAR_HEIGHT 10 #define SPACEMETER_BARINDENT_NORMAL 2 #define SPACEMETER_BARINDENT_THEMED 4 #define SPACEMETER_BARINDENT_BOTTOM 16 #define SPACEMETER_METER_SPACING 2 #define SPACEMETER_METER_HEIGHT 2 #define SPACEMETER_METER_COUNT 10 #define SPACEMETER_METERTEXT_SIZE 16 #define SPACEMETER_METERTEXT_INDENT_LEFT 4 /* New Tango colors. */ // Normal colors. #define SPACEMETER_BORDERCOLOR RGB(32,74,135) #define SPACEMETER_BARCOLOR_FREETOP RGB(114,159,205) #define SPACEMETER_BARCOLOR_FREEBOTTOM RGB(255,255,255) #define SPACEMETER_BARCOLOR_TOP RGB(114,159,205) #define SPACEMETER_BARCOLOR_BOTTOM RGB(52,101,164) // Warning colors (when overburning will most probably work). #define SPACEMETER_WARNBORDERCOLOR RGB(206,92,0) #define SPACEMETER_WARNBARCOLOR_FREETOP RGB(252,175,62) #define SPACEMETER_WARNBARCOLOR_FREEBOTTOM RGB(255,255,255) #define SPACEMETER_WARNBARCOLOR_TOP RGB(252,175,62) #define SPACEMETER_WARNBARCOLOR_BOTTOM RGB(245,121,0) // Disc full colors. #define SPACEMETER_FULLBORDERCOLOR RGB(164,0,0) #define SPACEMETER_FULLBARCOLOR_FREETOP RGB(239,41,41) #define SPACEMETER_FULLBARCOLOR_FREEBOTTOM RGB(255,255,255) #define SPACEMETER_FULLBARCOLOR_TOP RGB(239,41,41) #define SPACEMETER_FULLBARCOLOR_BOTTOM RGB(204,0,0) // How many bytes is it safe to overburn. #define SPACEMETER_OVERBURNSIZE 13516800 // 6600 * 2048 = 13 MiB. #define SPACEMETER_OVERBURNLENGTH 88 * 1000 // 6600 sectors = 88 seconds. #define SPACEMETER_DMSIZE 0 #define SPACEMETER_DMLENGTH 1 // Different draw states. #define SPACEMETER_DRAWSTATE_NORMAL 0 #define SPACEMETER_DRAWSTATE_WARN 1 #define SPACEMETER_DRAWSTATE_FULL 2 #define SPACEMETER_DRAWSTATE_OUTOFSCOPE 3 // Disc sizes (that should be passed to SetDiscSize). #define SPACEMETER_SIZE_DLDVD 0 #define SPACEMETER_SIZE_DVD 1 #define SPACEMETER_SIZE_870MB 2 #define SPACEMETER_SIZE_791MB 3 #define SPACEMETER_SIZE_703MB 4 #define SPACEMETER_SIZE_650MB 5 #define SPACEMETER_SIZE_210MB 6 #define SPACEMETER_SIZE_185MB 7 #define SPACEMETER_SIZE_1020MIN 8 #define SPACEMETER_SIZE_510MIN 9 #define SPACEMETER_SIZE_99MIN 10 #define SPACEMETER_SIZE_90MIN 11 #define SPACEMETER_SIZE_80MIN 12 #define SPACEMETER_SIZE_74MIN 13 #define SPACEMETER_SIZE_24MIN 14 #define SPACEMETER_SIZE_21MIN 15 // Specifies which ID the first recent menu item will have, the second will have + 1 and so on. #define SPACEMETER_POPUPMENU_IDBASE 1000 #define SPACEMETER_POPUPMENU_COUNT 8 #define SPACEMETER_TOOLTIP_ID 1042 class CSpaceMeter : public CWindowImpl { private: // These values are for rendering, they should never be altered manually. int m_iMeterPosition; int m_iMeterSegmentSpacing; TCHAR m_uiMeterSegments[SPACEMETER_METER_COUNT][SPACEMETER_METERTEXT_SIZE]; HBRUSH m_hBarBorderBrush; HBRUSH m_hWarnBarBorderBrush; HBRUSH m_hFullBarBorderBrush; // Used for drawing a Vista meter. HTHEME m_hProgressTheme; // Horizontal indentation in pixels. int m_iHorIndent; int m_iDisplayMode; int m_iDrawState; // The following values can be changed from the outside using public functions. unsigned __int64 m_uiAllocatedSize; unsigned __int64 m_uiDiscSize; unsigned __int64 m_uiMeterSize; // How many bytes does the meter display. // Tooltip. CToolTipCtrl m_ToolTip; ckcore::tstring m_ToolTipText; // Popup menu. HMENU m_hPopupMenu; void FillPopupMenu(); void DrawBar(HDC hDC,RECT *pClientRect); void DrawFullBar(HDC hDC,RECT *pClientRect); void DrawMeter(HDC hDC,RECT *pClientRect,RECT *pBarRect); void UpdateMeter(int iClientWidth); void UpdateToolTip(); bool m_bIsUpdatePending; public: DECLARE_WND_CLASS(_T("ckSpaceMeter")); CSpaceMeter(); ~CSpaceMeter(); //void SetDiskSize(unsigned __int64 uiDiskSize); void SetDiscSize(unsigned int uiDiscSize); void SetAllocatedSize(unsigned __int64 uiAllocatedSize); void IncreaseAllocatedSize(unsigned __int64 uiSize); void DecreaseAllocatedSize(unsigned __int64 uiSize); unsigned __int64 GetAllocatedSize(); void SetDisplayMode(int iDisplayMode); void Initialize(); private: #if _ATL_VER <= 0x0300 BEGIN_MSG_MAP_EX(CSpaceMeter) #else BEGIN_MSG_MAP(CSpaceMeter) #endif MESSAGE_HANDLER(WM_CREATE,OnCreate) MESSAGE_HANDLER(WM_SIZE,OnSize) MESSAGE_HANDLER(WM_PAINT,OnPaint) MESSAGE_HANDLER(WM_ERASEBKGND,OnEraseBkgnd) MESSAGE_HANDLER(WM_RBUTTONDOWN,OnRButtonDown) //MESSAGE_HANDLER(WM_MOUSEMOVE,OnMouseMove) MESSAGE_HANDLER(WMU_SPACE_METER_DELAYED_UPDATE,OnDelayedUpdate) MESSAGE_RANGE_HANDLER(WM_MOUSEFIRST,WM_MOUSELAST,OnMouseMove) NOTIFY_CODE_HANDLER(TTN_GETDISPINFO,OnGetDispInfo) COMMAND_RANGE_HANDLER_EX(SPACEMETER_POPUPMENU_IDBASE,SPACEMETER_POPUPMENU_IDBASE + SPACEMETER_POPUPMENU_COUNT - 1,OnPopupMenuClick) END_MSG_MAP() LRESULT OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnRButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnDelayedUpdate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnGetDispInfo(int idCtrl,LPNMHDR pnmh,BOOL &bHandled); LRESULT OnPopupMenuClick(UINT uNotifyCode,int nID,CWindow wnd); void RequestDelayedUpdate(); }; ================================================ FILE: src/app/control/title_tip_list_view_ctrl.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "title_tip_list_view_ctrl.hh" #include /* IMPORTANT: Requires host to chain the message loop. */ CTitleTipListViewCtrl::CTitleTipListViewCtrl() { m_iCurrentItem = -1; m_bTrackingMouseLeave = false; } CTitleTipListViewCtrl::~CTitleTipListViewCtrl() { if (m_ToolTip.IsWindow()) m_ToolTip.DestroyWindow(); } bool CTitleTipListViewCtrl::Initialize() { m_ToolTip.Create(NULL,CWindow::rcDefault,NULL, WS_POPUP | TTS_NOPREFIX | TTS_ALWAYSTIP,WS_EX_TOPMOST); if (!m_ToolTip.IsWindow()) return false; // Fill the tool information structure. ::ZeroMemory(&m_ti,sizeof(m_ti)); m_ti.cbSize = sizeof(TOOLINFO); m_ti.uFlags = TTF_IDISHWND | TTF_TRACK | TTF_ABSOLUTE; m_ti.hwnd = GetParent(); m_ti.hinst = _Module.GetResourceInstance(); m_ti.uId = (unsigned int)m_hWnd; m_ti.lpszText = LPSTR_TEXTCALLBACK; m_ToolTip.AddTool(&m_ti); m_ToolTip.TrackActivate(&m_ti,FALSE); return true; } LRESULT CTitleTipListViewCtrl::OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { bHandled = false; // Make sure that the control has been initialized. if (!m_ToolTip.IsWindowEnabled()) return 0; // Track the mouse to see when it leaves the list view. if (!m_bTrackingMouseLeave) { TRACKMOUSEEVENT tme = { 0 }; tme.cbSize = sizeof(TRACKMOUSEEVENT); tme.dwFlags = TME_LEAVE; tme.hwndTrack = m_hWnd; TrackMouseEvent(&tme); m_bTrackingMouseLeave = true; } POINT ptCursor = { GET_X_LPARAM(lParam),GET_Y_LPARAM(lParam) }; unsigned int uiFlags = 0; int iItem = HitTest(ptCursor,&uiFlags); // Check if whe're hovering above an item. if (iItem != -1) { RECT rcItem; GetItemRect(iItem,&rcItem,LVIR_SELECTBOUNDS); RECT rcListView; GetClientRect(&rcListView); // Check if the item text is to long to be fully displayed. if (rcItem.right >= rcListView.right) { // Is the tool tip already visible? if (m_ToolTip.GetCurrentTool(NULL) != 0) { if (m_iCurrentItem != iItem) { m_iCurrentItem = iItem; m_ToolTip.TrackActivate(&m_ti,TRUE); } ClientToScreen(&rcItem); ClientToScreen(&ptCursor); m_ToolTip.TrackPosition(rcItem.left,rcItem.top); } else { m_ToolTip.TrackActivate(&m_ti,TRUE); m_iCurrentItem = iItem; } } else { // Do not display the tool tip. m_ToolTip.TrackActivate(&m_ti,FALSE); } } else { // Do not display the tool tip. m_ToolTip.TrackActivate(&m_ti,FALSE); } return 0; } LRESULT CTitleTipListViewCtrl::OnMouseLeave(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_bTrackingMouseLeave = false; RECT rcListView; GetClientRect(&rcListView); ClientToScreen(&rcListView); POINT ptCursor; GetCursorPos(&ptCursor); // Check if the cursor has left the list view control. if (!PtInRect(&rcListView,ptCursor)) { if (m_ToolTip.IsWindow()) m_ToolTip.TrackActivate(&m_ti,FALSE); } bHandled = false; return 0; } LRESULT CTitleTipListViewCtrl::OnGetDispInfo(int idCtrl,LPNMHDR pnmh,BOOL &bHandled) { // Make sure that the notification is about the control we care about. if (pnmh->hwndFrom != m_ToolTip) { bHandled = FALSE; return 0; } // Copy the item title to the hint string buffer. LPNMTTDISPINFO pNMTDI = (LPNMTTDISPINFO)pnmh; GetItemText(m_iCurrentItem,0,pNMTDI->lpszText,80); return 0; } ================================================ FILE: src/app/control/title_tip_list_view_ctrl.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CTitleTipListViewCtrl : public CWindowImpl { private: CToolTipCtrl m_ToolTip; TOOLINFO m_ti; bool m_bTrackingMouseLeave; // The current item that's beeing hovered. int m_iCurrentItem; public: DECLARE_WND_CLASS(_T("ckToolTipListViewCtrl")); CTitleTipListViewCtrl(); ~CTitleTipListViewCtrl(); bool Initialize(); BEGIN_MSG_MAP(CTitleTipListViewCtrl) MESSAGE_HANDLER(WM_MOUSEMOVE,OnMouseMove) MESSAGE_HANDLER(WM_MOUSELEAVE,OnMouseLeave) NOTIFY_CODE_HANDLER(TTN_GETDISPINFO,OnGetDispInfo) END_MSG_MAP() LRESULT OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnMouseLeave(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnGetDispInfo(int idCtrl,LPNMHDR pnmh,BOOL &bHandled); }; ================================================ FILE: src/app/control/welcome_pane.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "resource.h" #include "main_frm.hh" #include "project_manager.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "action_manager.hh" #include "welcome_pane.hh" CWelcomePane::CStandardButton::CStandardButton(CWelcomePane *pParent, unsigned short usImageId, int iX,int iY,long lCtrlId) : CButton(pParent,iX,iY),m_State(STATE_NORMAL),m_bFocus(false),m_lCtrlId(lCtrlId) { m_Image.Open(usImageId); } void CWelcomePane::CStandardButton::Draw(HDC hDC) { switch (m_State) { case STATE_NORMAL: if (m_bFocus) { m_pParent->m_StandardFocusImage.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } else { m_pParent->m_StandardNormalImage.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } break; case STATE_HOT: if (m_bFocus) { m_pParent->m_StandardHoverFocusImage.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } else { m_pParent->m_StandardHoverImage.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } break; } m_Image.Draw(hDC,GetX() + 18,GetY() + 12,GetX() + 18 + BUTTON_WIDTH,GetY() + 12 + BUTTON_HEIGHT); } bool CWelcomePane::CStandardButton::HoverTest(int iX,int iY,bool &bChanged) { bool bHitX = iX > GetX() && iX < GetX() + BUTTON_WIDTH; bool bHitY = iY > GetY() && iY < GetY() + BUTTON_HEIGHT; if (bHitX && bHitY) { // Update status bar. if (m_State != STATE_HOT) m_pParent->SetStatusText(m_lCtrlId); bChanged = m_State != STATE_HOT; m_State = STATE_HOT; return true; } bChanged = m_State != STATE_NORMAL; m_State = STATE_NORMAL; return false; } long CWelcomePane::CStandardButton::ClickTest(int iX,int iY) { bool bHitX = iX > GetX() && iX < GetX() + BUTTON_WIDTH; bool bHitY = iY > GetY() && iY < GetY() + BUTTON_HEIGHT; if (bHitX && bHitY) return m_lCtrlId; return -1; } CWelcomePane::CMultiButton::CMultiButton(CWelcomePane *pParent, unsigned short usImageId, int iX,int iY, long lCtrlMainId, long lCtrlSub1Id, long lCtrlSub2Id) : CButton(pParent,iX,iY),m_State(STATE_NORMAL),m_bFocus(false), m_lCtrlMainId(lCtrlMainId),m_lCtrlSub1Id(lCtrlSub1Id),m_lCtrlSub2Id(lCtrlSub2Id) { m_Image.Open(usImageId); } void CWelcomePane::CMultiButton::Draw(HDC hDC) { switch (m_State) { case STATE_NORMAL: if (m_bFocus) { m_pParent->m_MultiFocusImage.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } else { m_pParent->m_MultiNormalImage.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } break; case STATE_HOTMAIN: if (m_bFocus) { m_pParent->m_MultiHoverFocusImage.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } else { m_pParent->m_MultiHoverImage.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } break; case STATE_HOTSUB1: if (m_bFocus) { m_pParent->m_MultiHoverFocusSub1Image.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } else { m_pParent->m_MultiHoverSub1Image.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } break; case STATE_HOTSUB2: if (m_bFocus) { m_pParent->m_MultiHoverFocusSub2Image.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } else { m_pParent->m_MultiHoverSub2Image.Draw(hDC,GetX(),GetY(), GetX() + BUTTON_WIDTH,GetY() + BUTTON_HEIGHT); } break; } m_Image.Draw(hDC,GetX() + 15,GetY() + 12,GetX() + 18 + BUTTON_WIDTH,GetY() + 12 + BUTTON_HEIGHT); } bool CWelcomePane::CMultiButton::HoverTest(int iX,int iY,bool &bChanged) { bool bHitX = iX > GetX() && iX < GetX() + BUTTON_WIDTH; bool bHitY = iY > GetY() && iY < GetY() + BUTTON_HEIGHT; if (bHitX && bHitY) { int iSplitterX = GetX() + SPLITTER_X; int iSplitterY = GetY() + SPLITTER_Y; long lCtrlId; eState NewState; if (iX < iSplitterX) { lCtrlId = m_lCtrlMainId; NewState = STATE_HOTMAIN; } else if (iY < iSplitterY) { lCtrlId = m_lCtrlSub1Id; NewState = STATE_HOTSUB1; } else { lCtrlId = m_lCtrlSub2Id; NewState = STATE_HOTSUB2; } // Update status bar. if (NewState != m_State) m_pParent->SetStatusText(lCtrlId); bChanged = NewState != m_State; m_State = NewState; return true; } bChanged = m_State != STATE_NORMAL; m_State = STATE_NORMAL; return true; } long CWelcomePane::CMultiButton::ClickTest(int iX,int iY) { bool bHitX = iX > GetX() && iX < GetX() + BUTTON_WIDTH; bool bHitY = iY > GetY() && iY < GetY() + BUTTON_HEIGHT; if (bHitX && bHitY) { int iSplitterX = GetX() + SPLITTER_X; int iSplitterY = GetY() + SPLITTER_Y; if (iX < iSplitterX) return m_lCtrlMainId; else if (iY < iSplitterY) return m_lCtrlSub1Id; else return m_lCtrlSub2Id; } return -1; } CWelcomePane::CWelcomePane() { //m_LogoImage.Open(_T("C:\\test.png")); m_LogoImage.Open(IDR_WELCOMELOGOPNG); // Load button images. m_StandardNormalImage.Open(IDR_BUTTONNPNG); m_StandardFocusImage.Open(IDR_BUTTONFPNG); m_StandardHoverImage.Open(IDR_BUTTONHPNG); m_StandardHoverFocusImage.Open(IDR_BUTTONHFPNG); // Load multi button images. m_MultiNormalImage.Open(IDR_MBUTTONNPNG); m_MultiFocusImage.Open(IDR_MBUTTONFPNG); m_MultiHoverImage.Open(IDR_MBUTTONHPNG); m_MultiHoverSub1Image.Open(IDR_MBUTTONHS1PNG); m_MultiHoverSub2Image.Open(IDR_MBUTTONHS2PNG); m_MultiHoverFocusImage.Open(IDR_MBUTTONFPNG); m_MultiHoverFocusSub1Image.Open(IDR_MBUTTONHFS1PNG); m_MultiHoverFocusSub2Image.Open(IDR_MBUTTONHFS2PNG); // Add buttons. m_Buttons.push_back(new CMultiButton(this,IDR_WIZARDDATAPNG, CButton::BUTTON_WIDTH * 0 + 10,10, ID_NEWPROJECT_DATA,ID_NEWPROJECT_DATACD,ID_NEWPROJECT_DATADVD)); m_Buttons.push_back(new CStandardButton(this,IDR_WIZARDAUDIOPNG, CButton::BUTTON_WIDTH * 1 + 10,10, ID_NEWPROJECT_AUDIO)); m_Buttons.push_back(new CStandardButton(this,IDR_WIZARDVIDEOPNG, CButton::BUTTON_WIDTH * 2 + 10,10, ID_NEWPROJECT_DVDVIDEO)); m_Buttons.push_back(new CStandardButton(this,IDR_WIZARDWRITEPNG, CButton::BUTTON_WIDTH * 0 + 10,CButton::BUTTON_HEIGHT + 10, ID_ACTIONS_BURNIMAGE)); m_Buttons.push_back(new CStandardButton(this,IDR_WIZARDCOPYPNG, CButton::BUTTON_WIDTH * 1 + 10,CButton::BUTTON_HEIGHT + 10, ID_COPYDISC_COMPACTDISC)); m_Buttons.push_back(new CStandardButton(this,IDR_WIZARDREADPNG, CButton::BUTTON_WIDTH * 2 + 10,CButton::BUTTON_HEIGHT + 10, ID_COPYDISC_DISCIMAGE)); } CWelcomePane::~CWelcomePane() { // Delete all buttons. std::vector::iterator itButton; for (itButton = m_Buttons.begin(); itButton != m_Buttons.end(); itButton++) delete *itButton; m_Buttons.clear(); } void CWelcomePane::SetStatusText(long lCtrlId) { bool bSuccess = false; if (g_LanguageSettings.m_pLngProcessor != NULL && g_LanguageSettings.m_pLngProcessor->EnterSection(_T("hint"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(lCtrlId,szStrValue)) { ::SendMessage(g_pMainFrame->m_hWndStatusBar,SB_SETTEXT,0,(LPARAM)szStrValue); bSuccess = true; } } if (!bSuccess) { TCHAR szBuffer[256]; LoadString(_Module.GetResourceInstance(),lCtrlId,szBuffer,sizeof(szBuffer) / sizeof(TCHAR)); ::SendMessage(g_pMainFrame->m_hWndStatusBar,SB_SETTEXT,0,(LPARAM)szBuffer); } } LRESULT CWelcomePane::OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { PAINTSTRUCT ps; HDC hDC = BeginPaint(&ps); // Calculate client rectangle. RECT rcClient; GetClientRect(&rcClient); // Center the buttons. int iDrawWidth = CButton::BUTTON_WIDTH * 3 + 20; int iDrawHeight = CButton::BUTTON_HEIGHT * 2 + 10; int iOffsetX = (rcClient.right >> 1) - (iDrawWidth >> 1); int iOffsetY = (rcClient.bottom >> 1) - (iDrawHeight >> 1); std::vector::iterator itButton; for (itButton = m_Buttons.begin(); itButton != m_Buttons.end(); itButton++) (*itButton)->Offset(iOffsetX,iOffsetY); // Use double-buffering. HDC hMemDC = CreateCompatibleDC(hDC); HBITMAP hMemBitmap = CreateCompatibleBitmap(hDC,rcClient.right - rcClient.left, rcClient.bottom - rcClient.top); HBITMAP hOldBitmap = (HBITMAP)SelectObject(hMemDC,hMemBitmap); // Draw into the memory buffer. FillRect(hMemDC,&rcClient,GetSysColorBrush(COLOR_WINDOW)); m_LogoImage.Draw(hMemDC,LOGO_INDENT_LEFT,LOGO_INDENT_TOP,rcClient.right,rcClient.bottom); // Draw buttons. //std::vector::iterator itButton; for (itButton = m_Buttons.begin(); itButton != m_Buttons.end(); itButton++) (*itButton)->Draw(hMemDC); // Copy the memory buffer into the frame buffer. BitBlt(hDC,0,0,rcClient.right,rcClient.bottom,hMemDC,0,0,SRCCOPY); // Free memory buffer handles. SelectObject(hMemDC,hOldBitmap); DeleteObject(hMemBitmap); DeleteDC(hMemDC); EndPaint(&ps); return 0; } LRESULT CWelcomePane::OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { return 0; } LRESULT CWelcomePane::OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { int iPosX = GET_X_LPARAM(lParam); int iPosY = GET_Y_LPARAM(lParam); bool bRedraw = false,bHasHit = false; std::vector::iterator itButton; for (itButton = m_Buttons.begin(); itButton != m_Buttons.end(); itButton++) { CWelcomePane::CButton *pButton = *itButton; bool bChanged = false; if (pButton->HoverTest(iPosX,iPosY,bChanged)) bHasHit = true; if (bChanged) bRedraw = true; } if (bRedraw) { RECT rcClient; GetClientRect(&rcClient); InvalidateRect(&rcClient); } if (!bHasHit) ::SetWindowText(g_pMainFrame->m_hWndStatusBar,_T("")); return 0; } LRESULT CWelcomePane::OnLButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { int iPosX = GET_X_LPARAM(lParam); int iPosY = GET_Y_LPARAM(lParam); std::vector::iterator itButton; for (itButton = m_Buttons.begin(); itButton != m_Buttons.end(); itButton++) { CWelcomePane::CButton *pButton = *itButton; long lAction = pButton->ClickTest(iPosX,iPosY); switch (lAction) { case ID_NEWPROJECT_DATA: g_pMainFrame->ShowWelcomePane(false); break; case ID_NEWPROJECT_DATACD: g_pMainFrame->ShowWelcomePane(false); g_ProjectManager.NewDataProject(SPACEMETER_SIZE_703MB); break; case ID_NEWPROJECT_DATADVD: g_pMainFrame->ShowWelcomePane(false); g_ProjectManager.NewDataProject(SPACEMETER_SIZE_DVD); break; case ID_NEWPROJECT_AUDIO: g_pMainFrame->ShowWelcomePane(false); g_ProjectManager.NewAudioProject(SPACEMETER_SIZE_80MIN); break; case ID_NEWPROJECT_DVDVIDEO: g_pMainFrame->ShowWelcomePane(false); g_ProjectManager.NewDataProject(SPACEMETER_SIZE_DVD); g_ProjectSettings.m_iFileSystem = FILESYSTEM_DVDVIDEO; break; case ID_ACTIONS_BURNIMAGE: g_ActionManager.BurnImage(*g_pMainFrame,false); break; case ID_COPYDISC_COMPACTDISC: g_ActionManager.CopyDisc(*g_pMainFrame,false); break; case ID_COPYDISC_DISCIMAGE: g_ActionManager.CopyImage(*g_pMainFrame,false); break; } } return 0; } ================================================ FILE: src/app/control/welcome_pane.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "png_file.hh" #include "custom_button.hh" #include "custom_multi_button.hh" class CWelcomePane : public CWindowImpl { private: enum { LOGO_INDENT_LEFT = 10, LOGO_INDENT_TOP = 10 }; class CButton { public: enum { BUTTON_WIDTH = 125, BUTTON_HEIGHT = 72 }; private: int m_iX; int m_iY; int m_iOffsetX; int m_iOffsetY; protected: CWelcomePane *m_pParent; public: CButton(CWelcomePane *pParent,int iX,int iY) : m_pParent(pParent),m_iX(iX),m_iY(iY),m_iOffsetX(0),m_iOffsetY(0) {} virtual ~CButton() {}; void Offset(int iOffsetX,int iOffsetY) { m_iOffsetX = iOffsetX; m_iOffsetY = iOffsetY; } int GetX() { return m_iX + m_iOffsetX; } int GetY() { return m_iY + m_iOffsetY; } virtual void Draw(HDC hDC) = 0; virtual bool HoverTest(int iX,int iY,bool &bChanged) = 0; virtual long ClickTest(int iX,int iY) = 0; }; class CStandardButton : public CButton { private: enum eState { STATE_NORMAL, STATE_HOT }; bool m_bFocus; long m_lCtrlId; eState m_State; CPngFile m_Image; public: CStandardButton(CWelcomePane *pParent,unsigned short usImageId,int iX,int iY,long lCtrlId); void Draw(HDC hDC); bool HoverTest(int iX,int iY,bool &bChanged); long ClickTest(int iX,int iY); }; class CMultiButton : public CButton { private: enum { SPLITTER_X = 99, SPLITTER_Y = 36 }; enum eState { STATE_NORMAL, STATE_HOTMAIN, STATE_HOTSUB1, STATE_HOTSUB2 }; bool m_bFocus; long m_lCtrlMainId; long m_lCtrlSub1Id; long m_lCtrlSub2Id; eState m_State; CPngFile m_Image; public: CMultiButton(CWelcomePane *pParent,unsigned short usImageId,int iX,int iY, long lCtrlMainId,long lCtrlSub1Id,long lCtrlSub2Id); void Draw(HDC hDC); bool HoverTest(int iX,int iY,bool &bChanged); long ClickTest(int iX,int iY); }; std::vector m_Buttons; CPngFile m_LogoImage; CPngFile m_StandardNormalImage; CPngFile m_StandardFocusImage; CPngFile m_StandardHoverImage; CPngFile m_StandardHoverFocusImage; CPngFile m_MultiNormalImage; CPngFile m_MultiFocusImage; CPngFile m_MultiHoverImage; CPngFile m_MultiHoverSub1Image; CPngFile m_MultiHoverSub2Image; CPngFile m_MultiHoverFocusImage; CPngFile m_MultiHoverFocusSub1Image; CPngFile m_MultiHoverFocusSub2Image; void SetStatusText(long lCtrlId); public: CWelcomePane(); ~CWelcomePane(); void Initialize(); BEGIN_MSG_MAP(CWelcomePane) MESSAGE_HANDLER(WM_PAINT,OnPaint) MESSAGE_HANDLER(WM_ERASEBKGND,OnEraseBkgnd) MESSAGE_HANDLER(WM_MOUSEMOVE,OnMouseMove) MESSAGE_HANDLER(WM_LBUTTONDOWN,OnLButtonDown) REFLECT_NOTIFICATIONS() END_MSG_MAP() LRESULT OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnEraseBkgnd(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnLButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/core/cd_text.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "cd_text.hh" void CCdText::InitCRC() { // Compute basis polynomials. unsigned short usBasePoly[8]; usBasePoly[0] = CDTEXT_CRCPOLYNOMIAL; for (int i = 1; i < 8; i++) { usBasePoly[i] = usBasePoly[i - 1] << 1; if ((usBasePoly[i - 1] >> 15) & 1) usBasePoly[i] ^= usBasePoly[0]; usBasePoly[i] &= 0x0ffff; } // Calculate the table entries. for (int i = 0; i < 256; i++) { int iCurrent = i; m_usCRCTable[i] = 0; for (int j = 0; j < 8; j++) { if (iCurrent & 1) m_usCRCTable[i] ^= usBasePoly[j]; iCurrent >>= 1; } } } unsigned short CCdText::CalcCRC(unsigned char *pBuffer,unsigned int uiLength) { unsigned short usCRC = 0; for (int i = 0; i < (int)uiLength; i++) usCRC = (usCRC << 8) ^ m_usCRCTable[(usCRC >> 8) ^ pBuffer[i]]; return usCRC; } CCdText::CCdText() { Reset(); // Initialize the CRC table. InitCRC(); } CCdText::~CCdText() { m_TrackNames.clear(); m_ArtistNames.clear(); } void CCdText::Reset() { m_szAlbumName[0] = '\0'; m_szArtistName[0] = '\0'; m_uiBufferPos = 0; m_szBuffer[0] = '\0'; m_TrackNames.clear(); m_ArtistNames.clear(); } unsigned int CCdText::FindBufferEOS(unsigned int uiStart,unsigned int uiEnd) { for (unsigned int i = uiStart; i < uiEnd; i++) { if (m_szBuffer[i] == '\0') return i; } return 0; } unsigned int CCdText::ReadPacket(ckcore::File &File,unsigned long ulPID, unsigned long ulBlockInfo) { // If the buffer can't hold the data we abort. if (m_uiBufferPos + 12 >= CDTEXT_MAXFIELDSIZE) return 0; // Not currently used. /*unsigned char ucDBCC = (unsigned char)(ulBlockInfo & 0x80) >> 7; unsigned char ucBlockNumber = (unsigned char)(ulBlockInfo & 0x70) >> 4; unsigned char ucCharPos = (unsigned char)(ulBlockInfo & 0x0F);*/ if (File.read(m_szBuffer + m_uiBufferPos,12) == -1) return false; // Debug information. char szTemp[25]; sprintf(szTemp,"%d, %d, %d",(int)(ulPID & 0xFF0000) >> 16,(int)(ulPID & 0xFF00) >> 8,(int)ulPID & 0xFF); char szTemp2[13]; memcpy(szTemp2,m_szBuffer + m_uiBufferPos,12); szTemp2[12] = '\0'; unsigned int uiEOS = FindBufferEOS(m_uiBufferPos,m_uiBufferPos + 12); m_uiBufferPos += 12; if (uiEOS == 0) return 12; switch (ulPID & 0xFF) { case PTI_NAMETITLE: // If the second PID bytes is zero it's an album name, otherwise it's a track name. if (((ulPID & 0xFF00) >> 8) == 0) memcpy(m_szAlbumName,m_szBuffer,uiEOS + 1); else m_TrackNames.push_back(m_szBuffer); break; case PTI_NAMEPERFORMER: if (((ulPID & 0xFF00) >> 8) == 0) memcpy(m_szArtistName,m_szBuffer,uiEOS + 1); else m_ArtistNames.push_back(m_szBuffer); break; // We ignore all binary fields. //case PTI_DISCID: // The specification is ambiguous and states that this type contains binary and character data. //case PTI_GENREID: // The specification is ambiguous and states that this type contains binary and character data. case PTI_TOCINFO: case PTI_TOCINFO2: case PTI_SIZEINFO: MessageBox(NULL,_T(""),_T(""),MB_OK); return 12; default: /*char szTemp[255]; memcpy(szTemp,m_szBuffer,uiEOS + 1); MessageBoxA(NULL,szTemp,"default",MB_OK);*/ break; }; // Skip all null characters. while (m_szBuffer[uiEOS] == '\0') uiEOS++; m_uiBufferPos -= uiEOS; memcpy(m_szBuffer,m_szBuffer + uiEOS,m_uiBufferPos); return 12; } bool CCdText::ReadFile(const TCHAR *szFileName) { // Clear any previous data. Reset(); ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_READ)) return false; // Make sure that the file is not too large. ckcore::tint64 iFileSize = File.size(); if (iFileSize > 0xFFFFFFFF) return false; unsigned int uiDataSize = (unsigned int)File.size(); // Try to find a signature. unsigned long ulSignature = 0; if (File.read(&ulSignature,4) == -1) return false; if (ulSignature == CDTEXT_SIGNATURE) uiDataSize -= 4; else File.seek(0,ckcore::File::ckFILE_BEGIN); unsigned int uiNumPackets = uiDataSize/18; for (unsigned int i = 0; i < uiNumPackets; i++) { // Read header. unsigned long ulHeader = 0; if (File.read(&ulHeader,sizeof(unsigned long)) == -1) return false; // The first three bytes of the header is the Pack Type Indicator (PID), // the last byte contain block information. ReadPacket(File,ulHeader & 0xFFFFFF,(ulHeader & 0xFF000000) >> 24); // Skip the CRC-field. if (File.seek(2,ckcore::File::ckFILE_CURRENT) == -1) return false; } return true; } unsigned int CCdText::WriteText(ckcore::File &File,unsigned char ucType,unsigned char ucPID2, const char *szText,unsigned int uiCharPos) { unsigned char ucBuffer[18]; ucBuffer[0] = ucType; ucBuffer[1] = ucPID2; unsigned int uiCurrentPos = 0; unsigned int uiCurrentLen = (unsigned int)strlen(szText) + 1; // We want to include the terminating null character. // Copy any old data to the write-buffer. if (m_uiBufferPos > 0) { ucBuffer[1] = m_ucPrevPID2; memcpy(ucBuffer + 4,m_szBuffer,m_uiBufferPos); } // Write all full texts. while (uiCurrentPos < uiCurrentLen) { int iByteCount = min(12 - m_uiBufferPos,uiCurrentLen - uiCurrentPos - m_uiBufferPos); memcpy(ucBuffer + 4 + m_uiBufferPos,szText + uiCurrentPos,iByteCount); // Flush. if (iByteCount + m_uiBufferPos == 12) { ucBuffer[2] = m_ucBlockCount++; ucBuffer[3] = uiCharPos + uiCurrentPos; // CRC. unsigned short usCRC = CalcCRC(ucBuffer,16); usCRC ^= 0xFFFF; ucBuffer[16] = static_cast((usCRC & 0xFF00) >> 8); ucBuffer[17] = static_cast(usCRC & 0xFF); // Write. File.write(ucBuffer,18); m_uiBufferPos = 0; uiCurrentPos += iByteCount; // If we have just written a block associated with the previous we can now // safeley set the second PID to match the current string. if (ucBuffer[1] == m_ucPrevPID2) { ucBuffer[1] = ucPID2; uiCharPos = 0; } } else { memcpy(m_szBuffer + m_uiBufferPos,szText + uiCurrentPos,iByteCount); m_uiBufferPos += iByteCount; break; } } return uiCurrentPos; } void CCdText::FlushText(ckcore::File &File,unsigned char ucType,unsigned int uiCharPos) { // Is there anything to flush? if (m_uiBufferPos > 0) { unsigned char ucBuffer[18]; ucBuffer[0] = ucType; ucBuffer[1] = m_ucPrevPID2; ucBuffer[2] = m_ucBlockCount++; ucBuffer[3] = uiCharPos; memcpy(ucBuffer + 4,m_szBuffer,m_uiBufferPos); memset(ucBuffer + 4 + m_uiBufferPos,'\0',12 - m_uiBufferPos); // CRC. unsigned short usCRC = CalcCRC(ucBuffer,16); usCRC ^= 0xFFFF; ucBuffer[16] = static_cast((usCRC & 0xFF00) >> 8); ucBuffer[17] = static_cast(usCRC & 0xFF); // Flush. File.write(ucBuffer,18); m_uiBufferPos = 0; } } bool CCdText::WriteFile(const TCHAR *szFileName) { ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_WRITE)) return false; #ifdef CDTEXT_SAVESIGNATURE // Write a signature. unsigned long ulSignature = CDTEXT_SIGNATURE; fs_write(&ulSignature,4,hFile); #endif // Reset the internal counters. m_uiBufferPos = 0; m_ucBlockCount = 0; unsigned int uiCharPos = 0; // Track title information. if (m_szAlbumName[0] != '\0') { uiCharPos = WriteText(File,PTI_NAMETITLE,0,m_szAlbumName,uiCharPos); m_ucPrevPID2 = 0; } for (unsigned int i = 0; i < m_TrackNames.size(); i++) { uiCharPos = WriteText(File,PTI_NAMETITLE,(unsigned char)i + 1,m_TrackNames[i].c_str(),uiCharPos); m_ucPrevPID2 = i + 1; } FlushText(File,PTI_NAMETITLE,uiCharPos); uiCharPos = 0; // Track artist information. if (m_szArtistName[0] != '\0') { uiCharPos = WriteText(File,PTI_NAMEPERFORMER,0,m_szArtistName,uiCharPos); m_ucPrevPID2 = 0; } for (unsigned int i = 0; i < m_ArtistNames.size(); i++) { uiCharPos = WriteText(File,PTI_NAMEPERFORMER,(unsigned char)i + 1,m_ArtistNames[i].c_str(),uiCharPos); m_ucPrevPID2 = i + 1; } FlushText(File,PTI_NAMEPERFORMER,uiCharPos); uiCharPos = 0; return true; } bool CCdText::WriteFileEx(const TCHAR *szFileName,const TCHAR *szAlbumName, const TCHAR *szArtistName,std::vector &Tracks) { ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_WRITE)) return false; #ifdef CDTEXT_SAVESIGNATURE // Write a signature. unsigned long ulSignature = CDTEXT_SIGNATURE; if (File.write(&ulSignature,4) == -1) return false; #endif // Reset the internal counters. m_uiBufferPos = 0; m_ucBlockCount = 0; unsigned int uiCharPos = 0; char szBuffer[CDTEXT_MAXFIELDSIZE]; // Track title information. if (szAlbumName[0] != '\0') { UnicodeToAnsi(szBuffer,szAlbumName,sizeof(szBuffer)); uiCharPos = WriteText(File,PTI_NAMETITLE,0,szBuffer,uiCharPos); m_ucPrevPID2 = 0; } for (unsigned int i = 0; i < Tracks.size(); i++) { UnicodeToAnsi(szBuffer,Tracks[i]->GetAudioData()->szTrackTitle,sizeof(szBuffer)); uiCharPos = WriteText(File,PTI_NAMETITLE,(unsigned char)i + 1,szBuffer,uiCharPos); m_ucPrevPID2 = i + 1; } FlushText(File,PTI_NAMETITLE,uiCharPos); uiCharPos = 0; // Track artist information. if (szArtistName[0] != '\0') { UnicodeToAnsi(szBuffer,szArtistName,sizeof(szBuffer)); uiCharPos = WriteText(File,PTI_NAMEPERFORMER,0,szBuffer,uiCharPos); m_ucPrevPID2 = 0; } for (unsigned int i = 0; i < Tracks.size(); i++) { UnicodeToAnsi(szBuffer,Tracks[i]->GetAudioData()->szTrackArtist,sizeof(szBuffer)); uiCharPos = WriteText(File,PTI_NAMEPERFORMER,(unsigned char)i + 1,szBuffer,uiCharPos); m_ucPrevPID2 = i + 1; } FlushText(File,PTI_NAMEPERFORMER,uiCharPos); uiCharPos = 0; return true; } ================================================ FILE: src/app/core/cd_text.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include "tree_manager.hh" #define CDTEXT_SIGNATURE 0x2201 #define CDTEXT_MAXFIELDSIZE 160 //#define CDTEXT_CRCPOLYNOMIAL 0x8408 #define CDTEXT_CRCPOLYNOMIAL 0x1021 // Define if a 4 byte header should be stored in the beginning of each cd-text binary file. //#define CDTEXT_SAVESIGNATURE class CCdText { private: unsigned short m_usCRCTable[256]; char m_szBuffer[CDTEXT_MAXFIELDSIZE]; unsigned int m_uiBufferPos; unsigned char m_ucBlockCount; unsigned char m_ucPrevPID2; void Reset(); unsigned int FindBufferEOS(unsigned int uiStart,unsigned int uiEnd); unsigned int ReadPacket(ckcore::File &File,unsigned long ulPID,unsigned long ulBlockInfo); // CRC routines. void InitCRC(); unsigned short CalcCRC(unsigned char *pBuffer,unsigned int uiLength); // Write routines. unsigned int WriteText(ckcore::File &File,unsigned char ucType,unsigned char ucPID2, const char *szText,unsigned int uiCharPos); void FlushText(ckcore::File &File,unsigned char ucType,unsigned int uiCharPos); enum ePTI { PTI_NAMETITLE = 0x80, PTI_NAMEPERFORMER = 0x81, PTI_NAMEWRITER = 0x82, PTI_NAMESONGWRITER = 0x83, PTI_NAMEARRANGER = 0x84, PTI_MESSAGEARTIST = 0x85, PTI_DISCID = 0x86, PTI_GENREID = 0x87, PTI_TOCINFO = 0x88, PTI_TOCINFO2 = 0x89, PTI_RESERVED1 = 0x8A, PTI_RESERVED2 = 0x8B, PTI_RESERVED3 = 0x8C, PTI_RESERVED4 = 0x8D, PTI_UPCEAN = 0x8E, PTI_SIZEINFO = 0x8F }; public: CCdText(); ~CCdText(); char m_szAlbumName[CDTEXT_MAXFIELDSIZE]; char m_szArtistName[CDTEXT_MAXFIELDSIZE]; std::vector m_TrackNames; std::vector m_ArtistNames; bool ReadFile(const TCHAR *szFileName); bool WriteFile(const TCHAR *szFileName); bool WriteFileEx(const TCHAR *szFileName,const TCHAR *szAlbumName, const TCHAR *szArtistName,std::vector &Tracks); }; ================================================ FILE: src/app/core/cdrtools_parse_strings.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #define CDRTOOLS_COPYRIGHT "Cdrecord-ProDVD-ProBD-Clone" #define CDRTOOLS_COPYRIGHT_LENGTH 27 #define CDRTOOLS_SCSIBUS "scsibus" #define CDRTOOLS_SCSIBUS_LENGTH 7 #ifdef CDRKIT #define CDRTOOLS_ERROR "wodim: " #define CDRTOOLS_ERROR_LENGTH 7 #define CDRTOOLS_ERROR3 "readom: " #define CDRTOOLS_ERROR3_LENGTH 8 #define CDRTOOLS_ERROR4 "icedax: " #define CDRTOOLS_ERROR4_LENGTH 8 #else #define CDRTOOLS_ERROR "cdrecord: " #define CDRTOOLS_ERROR_LENGTH 10 #define CDRTOOLS_ERROR3 "readcd: " #define CDRTOOLS_ERROR3_LENGTH 8 #define CDRTOOLS_ERROR4 "cdda2wav: " #define CDRTOOLS_ERROR4_LENGTH 10 #endif #define CDRTOOLS_REMOVABLE "Removable " #define CDRTOOLS_REMOVABLE_LENGTH 10 #define CDRTOOLS_TYPE_CDROM "CD-ROM" #define CDRTOOLS_TYPE_CDROM_LENGTH 6 #define CDRTOOLS_TYPE_COMMUNICATION "Communication" #define CDRTOOLS_TYPE_COMMUNICATION_LENGTH 13 #define CDRTOOLS_TYPE_DISC "Disk" #define CDRTOOLS_TYPE_DISC_LENGTH 4 #define CDRTOOLS_TYPE_JUKEBOX "Juke Box" #define CDRTOOLS_TYPE_JUKEBOX_LENGTH 8 #define CDRTOOLS_TYPE_OPTICALSTORAGE "Optical Storage" #define CDRTOOLS_TYPE_OPTICALSTORAGE_LENGTH 15 #define CDRTOOLS_TYPE_PRINTER "Printer" #define CDRTOOLS_TYPE_PRINTER_LENGTH 7 #define CDRTOOLS_TYPE_PROCESSOR "Processor" #define CDRTOOLS_TYPE_PROCESSOR_LENGTH 9 #define CDRTOOLS_TYPE_SCANNER "Scanner" #define CDRTOOLS_TYPE_SCANNER_LENGTH 7 #define CDRTOOLS_TYPE_TAPE "Tape" #define CDRTOOLS_TYPE_TAPE_LENGTH 4 #define CDRTOOLS_TYPE_WORM "WORM" #define CDRTOOLS_TYPE_WORM_LENGTH 4 #define CDRTOOLS_WRITEFLAGS "Driver flags :" #define CDRTOOLS_WRITEFLAGS_LENGTH 16 #define CDRTOOLS_WRITEMODES "Supported modes:" #define CDRTOOLS_WRITEMODES_LENGTH 16 #define CDRTOOLS_GRACEBEGIN "Last chance" #define CDRTOOLS_GRACEBEGIN_LENGTH 11 #define CDRTOOLS_NOMEDIA "Cannot load media." #define CDRTOOLS_NOMEDIA_LENGTH 18 #define CDRTOOLS_CYGWINPATH "/cygdrive/" #define CDRTOOLS_CYGWINPATH_LENGTH 10 #define CDRTOOLS_NOSUPPORT "This drive or" #define CDRTOOLS_NOSUPPORT_LENGTH 13 #define CDRTOOLS_BLANK "BLANK" #define CDRTOOLS_BLANK_LENGTH 5 #define CDRTOOLS_STARTCDWRITE "Starting to write CD/DVD" #define CDRTOOLS_STARTCDWRITE_LENGTH 24 #define CDRTOOLS_BLANKTIME "Blanking time:" #define CDRTOOLS_BLANKTIME_LENGTH 14 #define CDRTOOLS_NODISC "No disk " #define CDRTOOLS_NODISC_LENGTH 8 #define CDRTOOLS_BLANKERROR "Cannot blank" #define CDRTOOLS_BLANKERROR_LENGTH 12 #define CDRTOOLS_BLANKUNSUP "Some drives do not" #define CDRTOOLS_BLANKUNSUP_LENGTH 18 #define CDRTOOLS_BLANKRETRY "Try again" #define CDRTOOLS_BLANKRETRY_LENGTH 9 #define CDRTOOLS_UNSUPPORTED "Unsupported " #define CDRTOOLS_UNSUPPORTED_LENGTH 12 #define CDRTOOLS_SECTOR "sector" #define CDRTOOLS_SECTOR_LENGTH 6 #define CDRTOOLS_VERSIONINFO "This version" #define CDRTOOLS_VERSIONINFO_LENGTH 12 #define CDRTOOLS_DVDINFO "If you need" #define CDRTOOLS_DVDINFO_LENGTH 11 #define CDRTOOLS_DVDGETINFO "Free test" #define CDRTOOLS_DVDGETINFO_LENGTH 9 #define CDRTOOLS_STARTTRACK "Starting new track" #define CDRTOOLS_STARTTRACK_LENGTH 18 #define CDRTOOLS_WRITEPREGAP "Writing pregap" #define CDRTOOLS_WRITEPREGAP_LENGTH 14 #define CDRTOOLS_FILLFIFO "Waiting for reader" #define CDRTOOLS_FILLFIFO_LENGTH 18 #define CDRTOOLS_WRITETIME "Writing time:" #define CDRTOOLS_WRITETIME_LENGTH 14 #define CDRTOOLS_FIXATE "Fixating..." #define CDRTOOLS_FIXATE_LENGTH 11 #define CDRTOOLS_FIXATETIME "Fixating time:" #define CDRTOOLS_FIXATETIME_LENGTH 14 #define CDRTOOLS_WARNINGCAP "WARNING:" #define CDRTOOLS_WARNINGCAP_LENGTH 8 #define CDRTOOLS_WRITEERROR "A write error" #define CDRTOOLS_WRITEERROR_LENGTH 13 #define CDRTOOLS_FILENOTFOUND "No such file or directory." #define CDRTOOLS_FILENOTFOUND_LENGTH 26 #define CDRTOOLS_TOTALTTSIZE "Total translation table" #define CDRTOOLS_TOTALTTSIZE_LENGTH 23 #define CDRTOOLS_BADAUDIOCODING "Inappropriate audio" #define CDRTOOLS_BADAUDIOCODING_LENGTH 19 #define CDRTOOLS_RELOADDRIVE "Re-load" #define CDRTOOLS_RELOADDRIVE_LENGTH 7 #define CDRTOOLS_TOTALTIME "Time total: " #define CDRTOOLS_TOTALTIME_LENGTH 12 #define CDRTOOLS_END "end: " #define CDRTOOLS_END_LENGTH 5 #define CDRTOOLS_ADDRESS "addr: " #define CDRTOOLS_ADDRESS_LENGTH 6 #define CDRTOOLS_IOERROR "Input/Output error. " #define CDRTOOLS_IOERROR_LENGTH 20 #define CDRTOOLS_SECTORERROR "Error on sector" #define CDRTOOLS_SECTORERROR_LENGTH 15 #define CDRTOOLS_RETRYSECTOR "Retrying from sector" #define CDRTOOLS_RETRYSECTOR_LENGTH 20 #define CDRTOOLS_C2ERRORS "C2 errors " #define CDRTOOLS_C2ERRORS_LENGTH 10 #define CDRTOOLS_PERCENTDONE "percent_done:" #define CDRTOOLS_PERCENTDONE_LENGTH 13 #define CDRTOOLS_DEPPDIR "Directories too deep" #define CDRTOOLS_DEEPDIR_LENGTH 20 #define CDRTOOLS_FOUNDDVDMEDIA "Found DVD" #define CDRTOOLS_FOUNDDVDMEDIA_LENGTH 9 #define CDRTOOLS_OPENSESSION "Cannot open new sess" #define CDRTOOLS_OPENSESSION_LENGTH 20 #define CDRTOOLS_DISCSPACEWARNING "Data may not fit on cur" #define CDRTOOLS_DISCSPACEWARNING_LENGTH 23 #define CDRTOOLS_TURNINGBFON "Turning BURN" #define CDRTOOLS_TURNINGBFON_LENGTH 12 #define CDRTOOLS_TOTALEXTENT "Total extent" #define CDRTOOLS_TOTALEXTENT_LENGTH 12 #define CDRTOOLS_SIZEOFBOOT "Size of boot" #define CDRTOOLS_SIZEOFBOOT_LENGTH 12 #define CDRTOOLS_ERRORLEADIN "Could not write Lead-in." #define CDRTOOLS_ERRORLEADIN_LENGTH 24 #define CDRTOOLS_ERRORINITDRIVE "Cannot init drive" #define CDRTOOLS_ERRORINITDRIVE_LENGTH 17 #define CDRTOOLS_DVDRWDUMMY "DVD+RW has no -du" #define CDRTOOLS_DVDRWDUMMY_LENGTH 17 #define CDRTOOLS_FIFO "fifo" #define CDRTOOLS_FIFO_LENGTH 4 ================================================ FILE: src/app/core/core.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "cdrtools_parse_strings.hh" #include "string_table.hh" #include "settings.hh" #include "log_dlg.hh" #include "lang_util.hh" #include "version.hh" #include "temp_manager.hh" #include "device_util.hh" #include "core2.hh" #include "core.hh" // FIXME: How come Windows 95 supports larger command lines than Windows 2000? // Windows 2000 seems to be the only OS that is limited to MAX_PATH. // http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dllproc/base/createprocess.asp // http://support.microsoft.com/default.aspx?scid=kb;en-us;830473 // // Possible solution? // http://blogs.msdn.com/oldnewthing/archive/2003/12/10/56028.aspx // http://blogs.msdn.com/oldnewthing/archive/2003/12/11/56043.aspx CCore g_Core; CCore::CCore() { m_iMode = -1; m_iStatusMode = SMODE_DEFAULT; m_bGraceTimeDone = false; m_bDummyMode = false; m_bErrorPathMode = true; m_uiCDRToolsPathLen = 0; m_pProgress = NULL; } CCore::~CCore() { m_TrackSize.clear(); } /* CCore::Initialize ----------------- Prepares the object. This function should be called in the beginning of all cdrtools related functions. */ void CCore::Initialize(int iMode,CAdvancedProgress *pProgress) { m_iMode = iMode; m_iStatusMode = SMODE_DEFAULT; m_bGraceTimeDone = false; m_bErrorPathMode = true; // By default we're looking for a cygwin path before error messages. m_uiCDRToolsPathLen = lstrlen(g_GlobalSettings.m_szCDRToolsPathCyg); m_pProgress = pProgress; // Remove all previous track information. m_TrackSize.clear(); m_uiCurrentTrack = 0; m_lNumCopies = 1; } void CCore::Reinitialize() { m_bGraceTimeDone = false; m_bErrorPathMode = true; // By default we're looking for a cygwin path before error messages. m_uiCDRToolsPathLen = lstrlen(g_GlobalSettings.m_szCDRToolsPathCyg); m_uiCurrentTrack = 0; } void CCore::CreateBatchFile(const char *szChangeDir,const char *szCommandLine,TCHAR *szBatchPath) { // FIXME: This is not very nice. ckcore::File BatchFile = ckcore::File::temp(g_GlobalSettings.m_szTempPath, ckT("InfraRecorder")); lstrcpy(szBatchPath,BatchFile.name().c_str()); // Delete the generated temporary file since we need a batch file. ckcore::File::remove(szBatchPath); ChangeFileExt(szBatchPath,_T(".bat")); CStringContainerA StringContainer; if (szChangeDir != NULL) StringContainer.m_szStrings.push_back(szChangeDir); StringContainer.m_szStrings.push_back(szCommandLine); StringContainer.SaveToFile(szBatchPath); } bool CCore::SafeLaunch(tstring &CommandLine,bool bWaitForProcess) { if (g_GlobalSettings.m_bLog) g_pLogDlg->print_line(_T(" Command line to run: %s"),CommandLine.c_str()); if (m_lNumCopies > 0) m_lNumCopies--; m_LastCmdLine = CommandLine; m_bLastWaitForProcess = bWaitForProcess; // If the command line is longer than 260 characters we need to take special // actions since all (only Windows 2000?) Windows versions older than XP are // limited to MAX_PATH. Windows XP supports 32K character command lines. if (CommandLine.length() > MAX_PATH - 1) { if (g_WinVer.m_ulMajorVersion < MAJOR_WINXP || (g_WinVer.m_ulMajorVersion == MAJOR_WINXP && g_WinVer.m_ulMinorVersion < MINOR_WINXP)) { // Windows NT4 and 2000 supports 2048 character command lines, I am not // sure if Windows 9x do. This needs to be checked. if (CommandLine.length() > 2047) { TCHAR szMessage[256]; lsnprintf_s(szMessage,256,lngGetString(ERROR_COMMANDLINE),2048); MessageBox(HWND_DESKTOP,szMessage,lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return false; } if (g_GlobalSettings.m_bLog) g_pLogDlg->print_line(_T(" Warning: The command line is %d characters long. Trying to execute through shell."),CommandLine.length()); TCHAR szBatchPath[MAX_PATH]; char *szCommandLine = new char[CommandLine.length() + 1]; UnicodeToAnsi(szCommandLine,CommandLine.c_str(),(int)CommandLine.length() + 1); // Create the batch file. CreateBatchFile(NULL,szCommandLine,szBatchPath); delete [] szCommandLine; TCHAR szBatchCmdLine[MAX_PATH + 2]; lstrcpy(szBatchCmdLine,_T("\"")); lstrcat(szBatchCmdLine,szBatchPath); lstrcat(szBatchCmdLine,_T("\"")); if (bWaitForProcess) { bool bResult = create(szBatchCmdLine); ckcore::File::remove(szBatchPath); if (bWaitForProcess) wait(); return bResult; } else { g_TempManager.AddObject(szBatchPath); bool bResult = create(szBatchCmdLine); if (bWaitForProcess) wait(); return bResult; } } // Windows XP supports maximum 32768 characters. else if (CommandLine.length() > 32767) { TCHAR szMessage[256]; lsnprintf_s(szMessage,256,lngGetString(ERROR_COMMANDLINE),2048); MessageBox(HWND_DESKTOP,szMessage,lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return false; } } bool bResult = create((TCHAR *)CommandLine.c_str()); if (bWaitForProcess) wait(); return bResult; } bool CCore::Relaunch() { if (m_lNumCopies <= 0 || m_LastCmdLine.size() == 0) return false; if (!m_pProgress->RequestNextDisc()) return false; // Launch the process from a separate thread since the current thread belongs // to the previous process. unsigned long ulThreadID = 0; HANDLE hThread = ::CreateThread(NULL,0,NextCopyThread,this,0,&ulThreadID); if (hThread != NULL) { ::CloseHandle(hThread); return true; } return false; } bool CCore::CheckGraceTime(const char *szBuffer) { // If the message: Starting to write CD/DVD... is received we know that the // grace count down time is about to start so we change the new line // delimiter to '.' since the gracetime is updated using the '\b' character. if (!strncmp(szBuffer,CDRTOOLS_STARTCDWRITE,CDRTOOLS_STARTCDWRITE_LENGTH)) { // Sometimes the "Starting to write CD/DVD..." string will reappear after the // grace time countdown. Because of that we only allow this delimiter change once. if (!m_bGraceTimeDone) add_block_delim('.'); return true; } else if (!strncmp(szBuffer,CDRTOOLS_GRACEBEGIN,CDRTOOLS_GRACEBEGIN_LENGTH)) { m_iStatusMode = SMODE_GRACETIME; char szMode[6]; // Can be "dummy" or "real". int iTimer = 0; sscanf(szBuffer,"Last chance to quit, starting %s write in %d seconds.",szMode,&iTimer); m_bDummyMode = szMode[0] == 'd'; // Update the status. m_pProgress->set_status(lngGetString(PROGRESS_GRACETIME),iTimer); return true; } return false; } bool CCore::CheckProgress(const char *szBuffer) { if (!strncmp(szBuffer,CDRTOOLS_STARTTRACK,CDRTOOLS_STARTTRACK_LENGTH)) { add_block_delim('.'); m_iStatusMode = SMODE_PREPROGRESS; return true; } return false; } void CCore::ErrorOutputCDRECORD(const char *szBuffer) { if (m_pProgress != NULL) { if (!strncmp(szBuffer,CDRTOOLS_NOMEDIA,CDRTOOLS_NOMEDIA_LENGTH)) m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_NOMEDIA)); else if (!strncmp(szBuffer,CDRTOOLS_BLANKERROR,CDRTOOLS_BLANKERROR_LENGTH)) m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_ERASE)); else if (!strncmp(szBuffer,CDRTOOLS_BLANKUNSUP,CDRTOOLS_BLANKUNSUP_LENGTH)) m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(INFO_UNSUPERASEMODE)); else if (!strncmp(szBuffer,CDRTOOLS_BLANKRETRY,CDRTOOLS_BLANKRETRY_LENGTH)) m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(INFO_ERASERETRY)); else if (!strncmp(szBuffer,CDRTOOLS_NODISC,CDRTOOLS_NODISC_LENGTH)) m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_NOMEDIA)); else if (!strncmp(szBuffer,CDRTOOLS_BADAUDIOCODING,CDRTOOLS_BADAUDIOCODING_LENGTH)) { TCHAR szMessage[MAX_PATH + 128]; lstrcpy(szMessage,lngGetString(FAILURE_AUDIOCODING)); TCHAR szFileName[MAX_PATH + 3]; AnsiToUnicode(szFileName,szBuffer + CDRTOOLS_BADAUDIOCODING_LENGTH + 10,sizeof(szFileName) / sizeof(wchar_t)); lstrcat(szMessage,szFileName); m_pProgress->notify(ckcore::Progress::ckERROR,szMessage); } else if (!strncmp(szBuffer,CDRTOOLS_UNSUPPORTED,CDRTOOLS_UNSUPPORTED_LENGTH)) { char *pBuffer = (char *)szBuffer + 12; if (!strncmp(pBuffer,CDRTOOLS_SECTOR,CDRTOOLS_SECTOR_LENGTH)) { int iSectorSize = 0; sscanf(pBuffer,"sector size %ld for %*[^\0]",&iSectorSize); m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_BADSECTORSIZE),iSectorSize); } } else if (!strncmp(szBuffer,CDRTOOLS_WRITEERROR,CDRTOOLS_WRITEERROR_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_WRITE)); } #ifndef CORE_DVD_SUPPORT else if (!strncmp(szBuffer,CDRTOOLS_FOUNDDVDMEDIA,CDRTOOLS_FOUNDDVDMEDIA_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckWARNING,lngGetString(FAILURE_DVDSUPPORT)); } #endif else if (!strncmp(szBuffer,CDRTOOLS_OPENSESSION,CDRTOOLS_OPENSESSION_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_OPENSESSION)); } else if (!strncmp(szBuffer,CDRTOOLS_WARNINGCAP,CDRTOOLS_WARNINGCAP_LENGTH)) // "WARNING:" Prefix. { char *pBuffer = (char *)szBuffer + CDRTOOLS_WARNINGCAP_LENGTH + 1; if (!strncmp(pBuffer,CDRTOOLS_DISCSPACEWARNING,CDRTOOLS_DISCSPACEWARNING_LENGTH)) m_pProgress->notify(ckcore::Progress::ckWARNING,lngGetString(WARNING_DISCSIZE)); } else if (!strncmp(szBuffer,CDRTOOLS_ERRORLEADIN,CDRTOOLS_ERRORLEADIN_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_WRITELEADIN)); // When called from BurnTracks/BurnCompilation we need to flag the operation as failed. m_bOperationRes = false; } else if (!strncmp(szBuffer,CDRTOOLS_ERRORINITDRIVE,CDRTOOLS_ERRORINITDRIVE_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_INITDRIVE)); // When called from BurnTracks/BurnCompilation we need to flag the operation as failed. m_bOperationRes = false; } else if (!strncmp(szBuffer,CDRTOOLS_DVDRWDUMMY,CDRTOOLS_DVDRWDUMMY_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_DVDRWDUMMY)); // When called from BurnTracks/BurnCompilation we need to flag the operation as failed. m_bOperationRes = false; } #ifdef CORE_IGNORE_ERRORINFOMESSAGES // Ingore error information messages. else if (!strncmp(szBuffer,CDRTOOLS_VERSIONINFO,CDRTOOLS_VERSIONINFO_LENGTH)) return; else if (!strncmp(szBuffer,CDRTOOLS_DVDINFO,CDRTOOLS_DVDINFO_LENGTH)) return; else if (!strncmp(szBuffer,CDRTOOLS_DVDGETINFO,CDRTOOLS_DVDGETINFO_LENGTH)) return; #endif #ifdef CORE_PRINT_UNSUPERRORMESSAGES // Print unhandled messages from cdrecord to the log window. #ifdef CORE_DVD_SUPPORT else if (!strncmp(szBuffer,CDRTOOLS_FOUNDDVDMEDIA,CDRTOOLS_FOUNDDVDMEDIA_LENGTH)) return; #endif else if (!strncmp(szBuffer,CDRTOOLS_TURNINGBFON,CDRTOOLS_TURNINGBFON_LENGTH)) return; else if (!strncmp(szBuffer,CDRTOOLS_FIFO,CDRTOOLS_FIFO_LENGTH)) return; else { m_pProgress->notify(ckcore::Progress::ckEXTERNAL, ckcore::string::ansi_to_auto<1024>(szBuffer).c_str()); } #endif } } void CCore::ErrorOutputREADCD(const char *szBuffer) { if (m_pProgress != NULL) { if (!strncmp(szBuffer,CDRTOOLS_IOERROR,CDRTOOLS_IOERROR_LENGTH)) { char *pBuffer = (char *)szBuffer + CDRTOOLS_IOERROR_LENGTH; if (!strncmp(pBuffer,CDRTOOLS_SECTORERROR,CDRTOOLS_SECTORERROR_LENGTH)) { unsigned long ulSector = atoi(pBuffer + CDRTOOLS_SECTORERROR_LENGTH + 1); m_pProgress->notify(ckcore::Progress::ckWARNING,lngGetString(ERROR_SECTOR),ulSector); } } else if (!strncmp(szBuffer,CDRTOOLS_RETRYSECTOR,CDRTOOLS_RETRYSECTOR_LENGTH)) { unsigned long ulSector = atoi(szBuffer + CDRTOOLS_RETRYSECTOR_LENGTH + 1); m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_READSOURCEDISC),ulSector); } #ifdef CORE_PRINT_UNSUPERRORMESSAGES else { m_pProgress->notify(ckcore::Progress::ckEXTERNAL, ckcore::string::ansi_to_auto<1024>(szBuffer).c_str()); } #endif } } void CCore::ErrorOutputCDDA2WAV(const char *szBuffer) { } void CCore::EraseOutput(const char *szBuffer) { // Check if the media or command is not supported by the drive. if (!strncmp(szBuffer,CDRTOOLS_NOSUPPORT,CDRTOOLS_NOSUPPORT_LENGTH)) { char *pBuffer = (char *)szBuffer + 42; if (!strncmp(pBuffer,CDRTOOLS_BLANK,CDRTOOLS_BLANK_LENGTH)) m_pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_UNSUPRW)); } else if (CheckGraceTime(szBuffer)) { return; } else if (!strncmp(szBuffer,CDRTOOLS_BLANKTIME,CDRTOOLS_BLANKTIME_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_ERASE)); } else if (!strncmp(szBuffer,CDRTOOLS_RELOADDRIVE,CDRTOOLS_RELOADDRIVE_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckWARNING,lngGetString(FAILURE_LOADDRIVE)); m_pProgress->set_status(lngGetString(ERROR_RELOADDRIVE)); // Enable the reload button. m_pProgress->AllowReload(); } } void CCore::FixateOutput(const char *szBuffer) { if (CheckGraceTime(szBuffer)) { return; } else if (!strncmp(szBuffer,CDRTOOLS_FIXATETIME,CDRTOOLS_FIXATETIME_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_FIXATE)); } else if (!strncmp(szBuffer,CDRTOOLS_RELOADDRIVE,CDRTOOLS_RELOADDRIVE_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckWARNING,lngGetString(FAILURE_LOADDRIVE)); m_pProgress->set_status(lngGetString(ERROR_RELOADDRIVE)); // Enable the reload button. m_pProgress->AllowReload(); } } void CCore::BurnImageOutput(const char *szBuffer) { if (CheckGraceTime(szBuffer)) return; if (CheckProgress(szBuffer)) return; if (!strncmp(szBuffer,CDRTOOLS_WRITEPREGAP,CDRTOOLS_WRITEPREGAP_LENGTH)) { int iTrack = 0; long lPos = 0; sscanf(szBuffer,"Writing pregap for track %d at %ld",&iTrack,&lPos); TCHAR szStatus[64]; lsnprintf_s(szStatus,64,lngGetString(STATUS_WRITEPREGAP),iTrack,lPos); m_pProgress->set_status(szStatus); } else if (!strncmp(szBuffer,CDRTOOLS_FILLFIFO,CDRTOOLS_FILLFIFO_LENGTH)) { m_pProgress->set_status(lngGetString(STATUS_FILLBUFFER)); } else if (!strncmp(szBuffer,CDRTOOLS_WRITETIME,CDRTOOLS_WRITETIME_LENGTH)) { // Only display the error message if no error occured. if (m_bOperationRes) m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_WRITE)); } else if (!strncmp(szBuffer,CDRTOOLS_FIXATE,CDRTOOLS_FIXATE_LENGTH)) { m_pProgress->set_status(lngGetString(STATUS_FIXATE)); } else if (!strncmp(szBuffer,CDRTOOLS_FIXATETIME,CDRTOOLS_FIXATETIME_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_FIXATE)); } else if (!strncmp(szBuffer,CDRTOOLS_WARNINGCAP,CDRTOOLS_WARNINGCAP_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckWARNING,lngGetString(WARNING_FIXATE)); } else if (!strncmp(szBuffer,CDRTOOLS_RELOADDRIVE,CDRTOOLS_RELOADDRIVE_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckWARNING,lngGetString(FAILURE_LOADDRIVE)); m_pProgress->set_status(lngGetString(ERROR_RELOADDRIVE)); // Enable the reload button. m_pProgress->AllowReload(); } } void CCore::ReadDataTrackOutput(const char *szBuffer) { if (!strncmp(szBuffer,CDRTOOLS_END,CDRTOOLS_END_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINREADTRACK),m_TrackSize[1]); m_pProgress->set_status(lngGetString(STATUS_READTRACK)); } else if (!strncmp(szBuffer,CDRTOOLS_ADDRESS,CDRTOOLS_ADDRESS_LENGTH)) { unsigned __int64 uiAddress = 0; unsigned __int64 uiCount = 0; if (sscanf(szBuffer,"addr: %8ld cnt: %ld",&uiAddress,&uiCount) == 2) m_pProgress->set_progress((unsigned char)(((double)(uiAddress - m_TrackSize[0])/m_uiTotalSize) * 100)); } else if (!strncmp(szBuffer,CDRTOOLS_TOTALTIME,CDRTOOLS_TOTALTIME_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_READTRACK),m_TrackSize[1]); m_bOperationRes = true; // Success. } } void CCore::ReadAudioTrackOutput(const char *szBuffer) { if (!strncmp(szBuffer,CDRTOOLS_PERCENTDONE,CDRTOOLS_PERCENTDONE_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINREADTRACK),m_uiTotalSize); m_pProgress->set_status(lngGetString(STATUS_READTRACK)); m_iStatusMode = SMODE_AUDIOPROGRESS; } } void CCore::ScanTrackOutput(const char *szBuffer) { if (!strncmp(szBuffer,CDRTOOLS_END,CDRTOOLS_END_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINSCANTRACK),m_TrackSize[1]); m_pProgress->set_status(lngGetString(STATUS_SCANTRACK)); } else if (!strncmp(szBuffer,CDRTOOLS_ADDRESS,CDRTOOLS_ADDRESS_LENGTH)) { unsigned __int64 uiAddress = 0; unsigned __int64 uiCount = 0; if (sscanf(szBuffer,"addr: %8ld cnt: %ld",&uiAddress,&uiCount) == 2) m_pProgress->set_progress((unsigned char)(((double)(uiAddress - m_TrackSize[0])/m_uiTotalSize) * 100)); } else if (!strncmp(szBuffer,CDRTOOLS_TOTALTIME,CDRTOOLS_TOTALTIME_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_SCANTRACK),m_TrackSize[1]); m_bOperationRes = true; // Success. } else if (!strncmp(szBuffer,CDRTOOLS_C2ERRORS,CDRTOOLS_C2ERRORS_LENGTH)) { char *pBuffer = (char *)szBuffer + CDRTOOLS_C2ERRORS_LENGTH; if (!strncmp(pBuffer,"total",5)) { unsigned long ulBytes = 0; unsigned long ulSectors = 0; if (sscanf(pBuffer + 7,"%ld bytes in %d sectors on disk",&ulBytes,&ulSectors) == 2) { m_pProgress->notify(ulSectors > 0 ? ckcore::Progress::ckWARNING : ckcore::Progress::ckINFORMATION, lngGetString(STATUS_C2TOTAL),ulBytes,ulBytes); } } else if (!strncmp(pBuffer,"rate",4)) { float fRate = (float)atof(pBuffer + 6); m_pProgress->notify(fRate > 0 ? ckcore::Progress::ckWARNING : ckcore::Progress::ckINFORMATION, lngGetString(STATUS_C2RATE),fRate); } } } void CCore::ReadDiscOutput(const char *szBuffer) { if (!strncmp(szBuffer,CDRTOOLS_END,CDRTOOLS_END_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINREADDISC)); m_pProgress->set_status(lngGetString(STATUS_READDISC)); // Update the total number of sectors to process. m_uiTotalSize = atoi(szBuffer + CDRTOOLS_END_LENGTH); // Prevent a crash if the above function fails. if (m_uiTotalSize == 0) m_uiTotalSize = 1; } else if (!strncmp(szBuffer,CDRTOOLS_ADDRESS,CDRTOOLS_ADDRESS_LENGTH)) { unsigned __int64 uiAddress = 0; unsigned __int64 uiCount = 0; if (sscanf(szBuffer,"addr: %8ld cnt: %ld",&uiAddress,&uiCount) == 2) m_pProgress->set_progress((unsigned char)(((double)uiAddress/m_uiTotalSize) * 100)); } else if (!strncmp(szBuffer,CDRTOOLS_TOTALTIME,CDRTOOLS_TOTALTIME_LENGTH)) { m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_READDISC)); m_bOperationRes = true; // Success. } } void CCore::event_output(const std::string &block) { // Write to the log. if (g_GlobalSettings.m_bLog && m_iStatusMode == SMODE_DEFAULT) { g_pLogDlg->print(_T(" > ")); g_pLogDlg->print_line(ckcore::string::ansi_to_auto<1024>(block.c_str()).c_str()); } // Always skip the copyright line. if (!strncmp(block.c_str(),CDRTOOLS_COPYRIGHT,CDRTOOLS_COPYRIGHT_LENGTH)) return; // Check for a cygwin path. if (m_bErrorPathMode) { if (!strncmp(block.c_str(),CDRTOOLS_CYGWINPATH,CDRTOOLS_CYGWINPATH_LENGTH)) { // An error message has been found. if (!strncmp(block.c_str() + m_uiCDRToolsPathLen,CDRTOOLS_ERROR,CDRTOOLS_ERROR_LENGTH)) { ErrorOutputCDRECORD(block.c_str() + m_uiCDRToolsPathLen + CDRTOOLS_ERROR_LENGTH); return; } else if (!strncmp(block.c_str() + m_uiCDRToolsPathLen,CDRTOOLS_ERROR3,CDRTOOLS_ERROR3_LENGTH)) { ErrorOutputREADCD(block.c_str() + m_uiCDRToolsPathLen + CDRTOOLS_ERROR3_LENGTH); return; } else if (!strncmp(block.c_str() + m_uiCDRToolsPathLen,CDRTOOLS_ERROR4,CDRTOOLS_ERROR4_LENGTH)) { ErrorOutputCDDA2WAV(block.c_str() + m_uiCDRToolsPathLen + CDRTOOLS_ERROR4_LENGTH); return; } } } else { // An error message has been found. if (!strncmp(block.c_str(),CDRTOOLS_ERROR,CDRTOOLS_ERROR_LENGTH)) { ErrorOutputCDRECORD(block.c_str() + CDRTOOLS_ERROR_LENGTH); return; } else if (!strncmp(block.c_str(),CDRTOOLS_ERROR3,CDRTOOLS_ERROR3_LENGTH)) { ErrorOutputREADCD(block.c_str() + CDRTOOLS_ERROR3_LENGTH); return; } else if (!strncmp(block.c_str(),CDRTOOLS_ERROR4,CDRTOOLS_ERROR4_LENGTH)) { ErrorOutputCDDA2WAV(block.c_str() + CDRTOOLS_ERROR4_LENGTH); return; } } // If we are in grace time mode we only look for timer updates. if (m_iStatusMode == SMODE_GRACETIME) { int iTimer = 0; sscanf(block.c_str(),"\b\b\b\b\b\b\b\b\b\b\b\b\b%4d seconds",&iTimer); // Update the status. m_pProgress->set_status(lngGetString(PROGRESS_GRACETIME),iTimer); // Leave grace time mode if the timer is 0. if (iTimer == 0) { m_iStatusMode = SMODE_DEFAULT; m_bGraceTimeDone = true; // We reset the line delimiter to the new line character. remove_block_delim('.'); // Add a new message to the progress window (and update its staus). switch (m_iMode) { case MODE_ERASE: m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINERASE), m_bDummyMode ? lngGetString(WRITEMODE_SIMULATION) : lngGetString(WRITEMODE_REAL)); m_pProgress->set_status(lngGetString(STATUS_ERASE)); break; case MODE_FIXATE: m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINFIXATE), m_bDummyMode ? lngGetString(WRITEMODE_SIMULATION) : lngGetString(WRITEMODE_REAL)); m_pProgress->set_status(lngGetString(STATUS_FIXATE)); break; case MODE_BURNIMAGE: case MODE_BURNIMAGEEX: m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINWRITE), m_bDummyMode ? lngGetString(WRITEMODE_SIMULATION) : lngGetString(WRITEMODE_REAL)); m_pProgress->set_status(lngGetString(STATUS_WRITEDATA)); break; }; // Start the smoke. //if (!m_bDummyMode) m_pProgress->StartSmoke(); m_pProgress->SetRealMode(true); } return; } else if (m_iStatusMode == SMODE_PREPROGRESS) { // Now we want to terminate the strings by the x (speed). add_block_delim('x'); // Change the mode to progress mode. m_iStatusMode = SMODE_PROGRESS; // notify the status window that we're starting to write a new track. m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINTRACK), m_uiCurrentTrack + 1); return; } else if (m_iStatusMode == SMODE_PROGRESS) { // "Track 01: 1 of 473 MB written (fifo 100%) [buf 100%] 0.3x" //int iTrack = 0; int iBuffer = 0; __int64 iWritten = 0; float fSpeed = 0.0f; char *pBuffer = (char *)block.c_str(); if (pBuffer[0] == '.') *pBuffer++; // Special parsing, cdrtools has a bad habit of only writing output that is // not zero. This only affects the FIFO and buffer size. We know that the // track number, written size (in MB) and the write speed is always included // (cdrecord.c). pBuffer += 6; //iTrack = atoi(pBuffer); // Skip the integer. pBuffer = SkipInteger(pBuffer); // Skip the ':' character. *pBuffer++; iWritten = _atoi64(pBuffer); // Skip the integer. pBuffer = SkipInteger(pBuffer); // Skip trailing whitespace. *pBuffer++; // Look for total size (currently ignored). if (!strncmp(pBuffer,"of ",3)) { pBuffer += 3; pBuffer = SkipInteger(pBuffer); // Skip trailing whitespace. *pBuffer++; } pBuffer += 11; // Look for FIFO (currently ignored). if (*pBuffer == '(') { pBuffer += 6; pBuffer = SkipInteger(pBuffer); // Skip the '%', ')' and whitespace character. pBuffer += 3; } // Look for buffer. if (*pBuffer == '[') { pBuffer += 5; iBuffer = atoi(pBuffer); pBuffer = SkipInteger(pBuffer); // Skip the '%', ']' and whitespace character. pBuffer += 3; } // Update: 2007-02-10. Skip BCAP information. if (*pBuffer == '|') pBuffer += 12; // Write speed. fSpeed = (float)atof(pBuffer); // Update the status. m_pProgress->set_status(lngGetString(STATUS_WRITE),m_uiCurrentTrack + 1,(int)m_TrackSize.size(),fSpeed); m_pProgress->set_progress((unsigned char)(((double)(iWritten + m_uiProcessedSize)/m_uiTotalSize) * 100)); m_pProgress->SetBuffer(iBuffer); // Check if we're done writing the track. if (iWritten != 0 && iWritten == static_cast<__int64>(m_TrackSize[m_uiCurrentTrack])) { m_uiCurrentTrack++; remove_block_delim('x'); // Leave the progress mode. m_iStatusMode = SMODE_DEFAULT; // Update the totoal processed size. m_uiProcessedSize += iWritten; } return; } else if (m_iStatusMode == SMODE_AUDIOPROGRESS) { int iProgress = atoi(block.c_str()); m_pProgress->set_progress((unsigned char)iProgress); if (iProgress == 100) { m_iStatusMode = SMODE_DEFAULT; m_pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_READTRACK),m_uiTotalSize); m_bOperationRes = true; // Success. } } switch (m_iMode) { case MODE_EJECT: break; case MODE_ERASE: EraseOutput(block.c_str()); break; case MODE_FIXATE: FixateOutput(block.c_str()); break; case MODE_BURNIMAGE: case MODE_BURNIMAGEEX: BurnImageOutput(block.c_str()); break; case MODE_READDATATRACK: case MODE_READDATATRACKEX: ReadDataTrackOutput(block.c_str()); break; case MODE_READAUDIOTRACK: case MODE_READAUDIOTRACKEX: ReadAudioTrackOutput(block.c_str()); break; case MODE_SCANTRACK: case MODE_SCANTRACKEX: ScanTrackOutput(block.c_str()); break; case MODE_READDISC: case MODE_READDISCEX: ReadDiscOutput(block.c_str()); break; }; } void CCore::event_finished() { ckcore::tuint32 uiExitCode = 0; exit_code(uiExitCode); if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::ProcessEnded")); g_pLogDlg->print_line(_T(" Process exited with code: %d."),uiExitCode); } switch (m_iMode) { case MODE_EJECT: break; case MODE_ERASE: case MODE_FIXATE: //case MODE_BURNIMAGE: case MODE_READDATATRACK: case MODE_READAUDIOTRACK: case MODE_SCANTRACK: case MODE_READDISC: m_pProgress->set_progress(100); m_pProgress->set_status(lngGetString(uiExitCode == 0 ? PROGRESS_DONE : PROGRESS_FAILED)); m_pProgress->NotifyCompleted(); break; case MODE_BURNIMAGE: m_pProgress->set_progress(100); m_pProgress->set_status(lngGetString(uiExitCode == 0 ? PROGRESS_DONE : PROGRESS_FAILED)); if (m_lNumCopies <= 0 || !Relaunch()) m_pProgress->NotifyCompleted(); break; //case MODE_BURNIMAGEEX: case MODE_READDATATRACKEX: case MODE_READAUDIOTRACKEX: case MODE_SCANTRACKEX: case MODE_READDISCEX: if (m_bOperationRes) { m_pProgress->set_progress(0); } else { m_pProgress->set_progress(100); m_pProgress->set_status(lngGetString(uiExitCode == 0 ? PROGRESS_DONE : PROGRESS_FAILED)); m_pProgress->NotifyCompleted(); } break; case MODE_BURNIMAGEEX: if (m_lNumCopies <= 0 || !Relaunch()) { if (m_bOperationRes) { m_pProgress->set_progress(0); } else { m_pProgress->set_progress(100); m_pProgress->set_status(lngGetString(uiExitCode == 0 ? PROGRESS_DONE : PROGRESS_FAILED)); m_pProgress->NotifyCompleted(); } } break; }; } bool CCore::EjectDisc(ckmmc::Device &Device,bool bWaitForProcess) { // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::EjectDisc")); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); } // Initialize this object. Initialize(MODE_EJECT); tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_WRITEAPP); CommandLine += _T("\" -eject dev="); CommandLine += NDeviceUtil::GetDeviceAddr(Device); return SafeLaunch(CommandLine,bWaitForProcess); } bool CCore::LoadDisc(ckmmc::Device &Device,bool bWaitForProcess) { // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::LoadDisc")); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); } // Initialize this object. Initialize(MODE_EJECT); tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_WRITEAPP); CommandLine += _T("\" -load dev="); CommandLine += NDeviceUtil::GetDeviceAddr(Device); return SafeLaunch(CommandLine,bWaitForProcess); } bool CCore::EraseDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress, int iMode,bool bForce,bool bEject,bool bSimulate) { // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::EraseDisc")); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); g_pLogDlg->print_line(_T(" Mode = %d, Force = %d, Eject = %d, Simulate = %d."), iMode,(int)bForce,(int)bEject,(int)bSimulate); } // Initialize this object. Initialize(MODE_ERASE,pProgress); tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_WRITEAPP); CommandLine += _T("\" -v -blank="); switch (iMode) { case 0: CommandLine += _T("all dev="); break; case 2: CommandLine += _T("unclose dev="); break; case 3: CommandLine += _T("session dev="); break; default: CommandLine += _T("fast dev="); break; } CommandLine += NDeviceUtil::GetDeviceAddr(Device); TCHAR szBuffer[64]; lsprintf(szBuffer,_T(" gracetime=%d"),g_GlobalSettings.m_iGraceTime); CommandLine += szBuffer; if (bForce) CommandLine += _T(" -force"); if (Device.support(ckmmc::Device::ckDEVICE_EJECT) && bEject) CommandLine += _T(" -eject"); if (Device.support(ckmmc::Device::ckDEVICE_TEST_WRITE) && bSimulate) CommandLine += _T(" -dummy"); return SafeLaunch(CommandLine,false); } bool CCore::FixateDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress, bool bEject,bool bSimulate) { // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::FixateDisc")); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); g_pLogDlg->print_line(_T(" Eject = %d, Simulate = %d."), (int)bEject,(int)bSimulate); } // Initialize this object. Initialize(MODE_FIXATE,pProgress); tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_WRITEAPP); CommandLine += _T("\" -v -fix dev="); CommandLine += NDeviceUtil::GetDeviceAddr(Device); TCHAR szBuffer[64]; lsprintf(szBuffer,_T(" gracetime=%d"),g_GlobalSettings.m_iGraceTime); CommandLine += szBuffer; if (Device.support(ckmmc::Device::ckDEVICE_EJECT) && bEject) CommandLine += _T(" -eject"); if (Device.support(ckmmc::Device::ckDEVICE_TEST_WRITE) && bSimulate) CommandLine += _T(" -dummy"); return SafeLaunch(CommandLine,false); } bool CCore::BurnImage(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,bool bWaitForProcess,bool bCloneMode) { // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::BurnImage")); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); g_pLogDlg->print_line(_T(" File = %s."),szFileName); g_pLogDlg->print_line(_T(" Eject = %d, Simulate = %d, BUP = %d, Pad tracks = %d, Close = %d, Overburn = %d, Swab = %d, Ignore size = %d, Immed = %d, Audio master = %d, Forcespeed = %d, VariRec (enabled) = %d, VariRec (value) = %d, Clone = %d."), (int)g_BurnImageSettings.m_bEject, (int)g_BurnImageSettings.m_bSimulate, (int)g_BurnImageSettings.m_bBUP, (int)g_BurnImageSettings.m_bPadTracks, (int)g_BurnImageSettings.m_bFixate, (int)g_BurnAdvancedSettings.m_bOverburn, (int)g_BurnAdvancedSettings.m_bSwab, (int)g_BurnAdvancedSettings.m_bIgnoreSize, (int)g_BurnAdvancedSettings.m_bImmed, (int)g_BurnAdvancedSettings.m_bAudioMaster, (int)g_BurnAdvancedSettings.m_bForceSpeed, (int)g_BurnAdvancedSettings.m_bVariRec, g_BurnAdvancedSettings.m_iVariRec, (int)bCloneMode); } // Initialize this object. Initialize(MODE_BURNIMAGE,pProgress); // For creating multiple copies. m_lNumCopies = g_BurnImageSettings.m_lNumCopies; // We need to specify the total size that we should record. m_uiProcessedSize = 0; m_uiTotalSize = ckcore::File::size(szFileName) / (1024 * 1024); // MB. m_TrackSize.push_back(m_uiTotalSize); tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_WRITEAPP); CommandLine += _T("\" -v dev="); CommandLine += NDeviceUtil::GetDeviceAddr(Device); // Clone. if (bCloneMode) CommandLine += _T(" -clone"); TCHAR szBuffer[64]; lsprintf(szBuffer,_T(" gracetime=%d"),g_GlobalSettings.m_iGraceTime); CommandLine += szBuffer; // FIFO. if (g_GlobalSettings.m_iFIFOSize != 4) { lsprintf(szBuffer,_T(" fs=%dm"),g_GlobalSettings.m_iFIFOSize); CommandLine += szBuffer; } // Eject. if (Device.support(ckmmc::Device::ckDEVICE_EJECT) && g_BurnImageSettings.m_bEject) { CommandLine += _T(" -eject"); } // Simulation. if (Device.support(ckmmc::Device::ckDEVICE_TEST_WRITE) && g_BurnImageSettings.m_bSimulate) { CommandLine += _T(" -dummy"); } // Write method. switch (g_BurnImageSettings.m_iWriteMethod) { case WRITEMETHOD_SAO: CommandLine += _T(" -sao"); break; case WRITEMETHOD_TAO: CommandLine += _T(" -tao"); break; case WRITEMETHOD_TAONOPREGAP: CommandLine += _T(" -tao pregap=0"); break; case WRITEMETHOD_RAW96R: CommandLine += _T(" -raw96r"); break; case WRITEMETHOD_RAW16: CommandLine += _T(" -raw16"); break; case WRITEMETHOD_RAW96P: CommandLine += _T(" -raw96p"); break; }; TCHAR szDriverOpts[128]; lstrcpy(szDriverOpts,_T(" driveropts=")); bool bUseDriverOpts = false; // Buffer underrun protection. if (Device.support(ckmmc::Device::ckDEVICE_BUP)) { bUseDriverOpts = true; if (g_BurnImageSettings.m_bBUP) lstrcat(szDriverOpts,_T("burnfree,")); else lstrcat(szDriverOpts,_T("noburnfree,")); } // Audio master. if (Device.support(ckmmc::Device::ckDEVICE_AUDIO_MASTER)) { if (g_BurnAdvancedSettings.m_bAudioMaster) { lstrcat(szDriverOpts,_T("audiomaster,")); bUseDriverOpts = true; } } // Forcespeed. if (Device.support(ckmmc::Device::ckDEVICE_FORCE_SPEED)) { if (!g_BurnAdvancedSettings.m_bForceSpeed) { lstrcat(szDriverOpts,_T("noforcespeed,")); bUseDriverOpts = true; } } // VariRec. if (Device.support(ckmmc::Device::ckDEVICE_VARIREC)) { if (g_BurnAdvancedSettings.m_bVariRec) { TCHAR szVariRec[32]; lsprintf(szVariRec,_T("varirec=%d,"),g_BurnAdvancedSettings.m_iVariRec); lstrcat(szDriverOpts,szVariRec); bUseDriverOpts = true; } } if (bUseDriverOpts) { szDriverOpts[lstrlen(szDriverOpts) - 1] = '\0'; CommandLine += szDriverOpts; } // Pad tracks. if (g_BurnImageSettings.m_bPadTracks) CommandLine += _T(" -pad"); // Fixate. if (!g_BurnImageSettings.m_bFixate) CommandLine += _T(" -nofix"); // Overburning. if (g_BurnAdvancedSettings.m_bOverburn) CommandLine += _T(" -overburn"); // Swap audio byte order. FIXME: Should possibly check for support before selecting. if (g_BurnAdvancedSettings.m_bSwab) CommandLine += _T(" -swab"); // Ignore size. if (g_BurnAdvancedSettings.m_bIgnoreSize) CommandLine += _T(" -ignsize"); // SCSI IMMED flag. if (g_BurnAdvancedSettings.m_bImmed) CommandLine += _T(" -immed"); // Speed. if (g_BurnImageSettings.m_iWriteSpeed != -1) { lsprintf(szBuffer,_T(" speed=%d"),g_BurnImageSettings.m_iWriteSpeed); CommandLine += szBuffer; } // File name. TCHAR szCygwinFileName[MAX_PATH + 16]; GetCygwinFileName(szFileName,szCygwinFileName); ckcore::Path FilePath(szFileName); if (!ckcore::string::astrcmpi(FilePath.ext_name().c_str(),ckT("cue"))) { CommandLine += _T(" cuefile=\""); CommandLine += szCygwinFileName; CommandLine += _T("\""); } else // any other. { CommandLine += _T(" \""); CommandLine += szCygwinFileName; CommandLine += _T("\""); } return SafeLaunch(CommandLine,bWaitForProcess); } bool CCore::BurnTracks(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szDataTrack,std::vector &AudioTracks, const TCHAR *szAudioText,int iDataMode,int iMode,bool bWaitForProcess) { // This function behaves different from almost all the others using // m_bOperationRes. It actually assumes a successfull writing until proved // otherwise. m_bOperationRes = true; // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::BurnTracks")); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); if (szDataTrack != NULL) g_pLogDlg->print_line(_T(" File = %s."),szDataTrack); g_pLogDlg->print_line(_T(" Eject = %d, Simulate = %d, BUP = %d, Pad tracks = %d, Close = %d, Method = %d, Overburn = %d, Swab = %d, Ignore size = %d, Immed = %d, Audio master = %d, Forcespeed = %d, VariRec (enabled) = %d, VariRec (value) = %d, Mode = %d."), (int)g_BurnImageSettings.m_bEject, (int)g_BurnImageSettings.m_bSimulate, (int)g_BurnImageSettings.m_bBUP, (int)g_BurnImageSettings.m_bPadTracks, (int)g_BurnImageSettings.m_bFixate, g_BurnImageSettings.m_iWriteMethod, (int)g_BurnAdvancedSettings.m_bOverburn, (int)g_BurnAdvancedSettings.m_bSwab, (int)g_BurnAdvancedSettings.m_bIgnoreSize, (int)g_BurnAdvancedSettings.m_bImmed, (int)g_BurnAdvancedSettings.m_bAudioMaster, (int)g_BurnAdvancedSettings.m_bForceSpeed, (int)g_BurnAdvancedSettings.m_bVariRec, g_BurnAdvancedSettings.m_iVariRec, iDataMode); } // Initialize this object. Initialize(iMode,pProgress); // We need to specify the total size that we should record. m_uiProcessedSize = 0; if (szDataTrack != NULL) { m_uiTotalSize = ckcore::File::size(szDataTrack) / (1024 * 1024); // MB. m_TrackSize.push_back(m_uiTotalSize); } else { m_uiTotalSize = 0; } for (unsigned int i = 0; i < AudioTracks.size(); i++) { unsigned __int64 uiTrackSize = ckcore::File::size(AudioTracks[i]) / (1024 * 1024); m_TrackSize.push_back(uiTrackSize); m_uiTotalSize += uiTrackSize; } tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_WRITEAPP); CommandLine += _T("\" -v dev="); CommandLine += NDeviceUtil::GetDeviceAddr(Device); TCHAR szBuffer[64]; lsprintf(szBuffer,_T(" gracetime=%d"),g_GlobalSettings.m_iGraceTime); CommandLine += szBuffer; // FIFO. if (g_GlobalSettings.m_iFIFOSize != 4) { lsprintf(szBuffer,_T(" fs=%dm"),g_GlobalSettings.m_iFIFOSize); CommandLine += szBuffer; } // Eject. if (Device.support(ckmmc::Device::ckDEVICE_EJECT) && g_BurnImageSettings.m_bEject) { CommandLine += _T(" -eject"); } // Simulation. if (Device.support(ckmmc::Device::ckDEVICE_TEST_WRITE) && g_BurnImageSettings.m_bSimulate) { CommandLine += _T(" -dummy"); } // Write method. switch (g_BurnImageSettings.m_iWriteMethod) { case WRITEMETHOD_SAO: CommandLine += _T(" -sao"); break; case WRITEMETHOD_TAO: CommandLine += _T(" -tao"); break; case WRITEMETHOD_TAONOPREGAP: CommandLine += _T(" -tao pregap=0"); break; case WRITEMETHOD_RAW96R: CommandLine += _T(" -raw96r"); break; case WRITEMETHOD_RAW16: CommandLine += _T(" -raw16"); break; case WRITEMETHOD_RAW96P: CommandLine += _T(" -raw96p"); break; }; TCHAR szDriverOpts[128]; lstrcpy(szDriverOpts,_T(" driveropts=")); bool bUseDriverOpts = false; // Buffer underrun protection. if (Device.support(ckmmc::Device::ckDEVICE_BUP)) { bUseDriverOpts = true; if (g_BurnImageSettings.m_bBUP) lstrcat(szDriverOpts,_T("burnfree,")); else lstrcat(szDriverOpts,_T("noburnfree,")); } // Audio master. if (Device.support(ckmmc::Device::ckDEVICE_AUDIO_MASTER)) { if (g_BurnAdvancedSettings.m_bAudioMaster) { lstrcat(szDriverOpts,_T("audiomaster,")); bUseDriverOpts = true; } } // Forcespeed. if (Device.support(ckmmc::Device::ckDEVICE_FORCE_SPEED)) { if (!g_BurnAdvancedSettings.m_bForceSpeed) { lstrcat(szDriverOpts,_T("noforcespeed,")); bUseDriverOpts = true; } } // VariRec. if (Device.support(ckmmc::Device::ckDEVICE_VARIREC)) { if (g_BurnAdvancedSettings.m_bVariRec) { TCHAR szVariRec[32]; lsprintf(szVariRec,_T("varirec=%d,"),g_BurnAdvancedSettings.m_iVariRec); lstrcat(szDriverOpts,szVariRec); bUseDriverOpts = true; } } if (bUseDriverOpts) { szDriverOpts[lstrlen(szDriverOpts) - 1] = '\0'; CommandLine += szDriverOpts; } // Pad tracks. if (g_BurnImageSettings.m_bPadTracks) CommandLine += _T(" -pad"); // Fixate. if (!g_BurnImageSettings.m_bFixate) CommandLine += _T(" -nofix"); // Overburning. if (g_BurnAdvancedSettings.m_bOverburn) CommandLine += _T(" -overburn"); // Swap audio byte order. // FIXME: Should probably check for support before selecting. if (g_BurnAdvancedSettings.m_bSwab) CommandLine += _T(" -swab"); // Ignore size. if (g_BurnAdvancedSettings.m_bIgnoreSize) CommandLine += _T(" -ignsize"); // SCSI IMMED flag. if (g_BurnAdvancedSettings.m_bImmed) CommandLine += _T(" -immed"); // Speed. if (g_BurnImageSettings.m_iWriteSpeed != -1) { lsprintf(szBuffer,_T(" speed=%d"),g_BurnImageSettings.m_iWriteSpeed); CommandLine += szBuffer; } // File name. TCHAR szCygwinFileName[MAX_PATH + 16]; if (szDataTrack != NULL) { // Mode. switch (iDataMode) { case 0: // Mode 1 CommandLine += _T(" -data"); break; case 1: // Mode 2 XA (multisession) CommandLine += _T(" -multi"); break; }; GetCygwinFileName(szDataTrack,szCygwinFileName); ckcore::Path FilePath(szDataTrack); if (!ckcore::string::astrcmpi(FilePath.ext_name().c_str(),ckT("cue"))) { CommandLine += _T(" cuefile=\""); CommandLine += szCygwinFileName; CommandLine += _T("\""); } else // any other. { CommandLine += _T(" \""); CommandLine += szCygwinFileName; CommandLine += _T("\""); } } // Audio tracks. if (AudioTracks.size() > 0) CommandLine += _T(" -audio"); for (unsigned int i = 0; i < AudioTracks.size(); i++) { GetCygwinFileName(AudioTracks[i],szCygwinFileName); CommandLine += _T(" \""); CommandLine += szCygwinFileName; CommandLine += _T("\""); } // Audio text. if (szAudioText != NULL) { CommandLine += _T(" textfile=\""); CommandLine += szAudioText; CommandLine += _T("\""); } return SafeLaunch(CommandLine,bWaitForProcess); } bool CCore::BurnImage(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,bool bCloneMode) { return BurnImage(Device,pProgress,szFileName,false,bCloneMode); } /* CCore::BurnImageEx ------------------ Same as the function above except that it will not return untill the process has ended. */ bool CCore::BurnImageEx(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,bool bCloneMode) { return BurnImage(Device,pProgress,szFileName,true,bCloneMode); } bool CCore::BurnTracks(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szDataTrack,std::vector &AudioTracks, const TCHAR *szAudioText,int iDataMode) { return BurnTracks(Device,pProgress,szDataTrack,AudioTracks,szAudioText, iDataMode,MODE_BURNIMAGE,true); } /* CCore::BurnTracksEx ------------------- Works like CCore::BurnTracks but it does not end the progress when done. It allows for more operations to be performed in the same progress window. It also has extra return values. */ eBurnResult CCore::BurnTracksEx(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szDataTrack,std::vector &AudioTracks, const TCHAR *szAudioText,int iDataMode) { if (!BurnTracks(Device,pProgress,szDataTrack,AudioTracks,szAudioText, iDataMode,MODE_BURNIMAGEEX,true)) { return BURNRESULT_INTERNALERROR; } ckcore::tuint32 uiExitCode = 0; exit_code(uiExitCode); return uiExitCode == 0 ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; //return m_bOperationRes ? RESULT_OK : RESULT_EXTERNALERROR; } /* CCore::ReadDataTrack -------------------- Reads a track from the CD and stores the raw binary content in the file named szFileName. */ bool CCore::ReadDataTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,unsigned int uiTrackNumber, unsigned long ulStartSector,unsigned long ulEndSector, int iMode,bool bWaitForProcess) { m_bOperationRes = false; // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::ReadDataTrack")); g_pLogDlg->print_line(_T(" File = %s."),szFileName); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); g_pLogDlg->print_line(_T(" Start = %d, End = %d."),ulStartSector,ulEndSector); } // Initialize this object. Initialize(iMode,pProgress); // We need to specify the end adresses (in sectors) that we should read. m_uiProcessedSize = 0; m_uiTotalSize = ulEndSector - ulStartSector; // Track length (in sectors). m_TrackSize.push_back(ulStartSector); // Start address of the track. m_TrackSize.push_back(uiTrackNumber); tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_READAPP); CommandLine += _T("\" dev="); CommandLine += NDeviceUtil::GetDeviceAddr(Device); // Sector range. TCHAR szBuffer[128]; lsprintf(szBuffer,_T(" sectors=%d-%d"),ulStartSector,ulEndSector); CommandLine += szBuffer; // File name. CommandLine += _T(" f=\""); CommandLine += szFileName; CommandLine += _T("\""); return SafeLaunch(CommandLine,bWaitForProcess); } bool CCore::ReadDataTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,unsigned int uiTrackNumber, unsigned long ulStartSector,unsigned long ulEndSector) { return ReadDataTrack(Device,pProgress,szFileName,uiTrackNumber, ulStartSector,ulEndSector,MODE_READDATATRACK,true); } eBurnResult CCore::ReadDataTrackEx(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,unsigned int uiTrackNumber, unsigned long ulStartSector,unsigned long ulEndSector) { if (!ReadDataTrack(Device,pProgress,szFileName,uiTrackNumber,ulStartSector, ulEndSector,MODE_READDATATRACKEX,true)) { return BURNRESULT_INTERNALERROR; } ckcore::tuint32 uiExitCode = 0; exit_code(uiExitCode); return uiExitCode == 0 ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; //return m_bOperationRes ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; } /* */ bool CCore::ReadAudioTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,unsigned int uiTrackNumber, int iMode,bool bWaitForProcess) { m_bOperationRes = false; // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::ReadAudioTrack")); g_pLogDlg->print_line(_T(" File = %s."),szFileName); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); } // Initialize this object. Initialize(iMode,pProgress); // Remember what track we are working with. m_uiTotalSize = uiTrackNumber; tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_AUDIOAPP); CommandLine += _T("\" -D "); CommandLine += NDeviceUtil::GetDeviceAddr(Device); // Miscellaneous. CommandLine += _T(" -I generic_scsi -x -B -O wav -g -H"); // Track. TCHAR szBuffer[128]; lsprintf(szBuffer,_T(" -t %d+%d"),uiTrackNumber,uiTrackNumber); CommandLine += szBuffer; // File name. CommandLine += _T(" \""); CommandLine += szFileName; CommandLine += _T("\""); return SafeLaunch(CommandLine,bWaitForProcess); } bool CCore::ReadAudioTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,unsigned int uiTrackNumber) { return ReadAudioTrack(Device,pProgress,szFileName,uiTrackNumber, MODE_READAUDIOTRACK,true); } eBurnResult CCore::ReadAudioTrackEx(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName, unsigned int uiTrackNumber) { if (!ReadAudioTrack(Device,pProgress,szFileName,uiTrackNumber, MODE_READAUDIOTRACKEX,true)) { return BURNRESULT_INTERNALERROR; } ckcore::tuint32 uiExitCode = 0; exit_code(uiExitCode); return uiExitCode == 0 ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; //return m_bOperationRes ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; } /* CCore::ScanTrack ---------------- Scans the selected track for CRC and C2 errors. */ bool CCore::ScanTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress, unsigned int uiTrackNumber,unsigned long ulStartSector, unsigned long ulEndSector,int iMode,bool bWaitForProcess) { m_bOperationRes = false; // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::ScanTrack")); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); g_pLogDlg->print_line(_T(" Start = %d, End = %d."),ulStartSector,ulEndSector); } // Initialize this object. Initialize(iMode,pProgress); // We need to specify the end adresses (in sectors) that we should read. m_uiProcessedSize = 0; m_uiTotalSize = ulEndSector - ulStartSector; // Track length (in sectors). m_TrackSize.push_back(ulStartSector); // Start address of the track. m_TrackSize.push_back(uiTrackNumber); tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_READAPP); CommandLine += _T("\" -c2scan dev="); CommandLine += NDeviceUtil::GetDeviceAddr(Device); // Sector range. TCHAR szBuffer[128]; lsprintf(szBuffer,_T(" sectors=%d-%d"),ulStartSector,ulEndSector); CommandLine += szBuffer; return SafeLaunch(CommandLine,bWaitForProcess); } bool CCore::ScanTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress,unsigned int uiTrackNumber, unsigned long ulStartSector,unsigned long ulEndSector) { return ScanTrack(Device,pProgress,uiTrackNumber,ulStartSector,ulEndSector, MODE_SCANTRACK,true); } eBurnResult CCore::ScanTrackEx(ckmmc::Device &Device,CAdvancedProgress *pProgress,unsigned int uiTrackNumber, unsigned long ulStartSector,unsigned long ulEndSector) { if (!ScanTrack(Device,pProgress,uiTrackNumber,ulStartSector,ulEndSector, MODE_SCANTRACKEX,true)) { return BURNRESULT_INTERNALERROR; } ckcore::tuint32 uiExitCode = 0; exit_code(uiExitCode); return uiExitCode == 0 ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; //return m_bOperationRes ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; } /* CCore::CopyDisc --------------- Performs an on-the-fly copy of a disc. This function is configured through the g_BurnImageSettings, g_BurnAdvancedSettings and g_ReadSettings (m_bIgnoreErr only) objects. */ bool CCore::CopyDisc(ckmmc::Device &SrcDevice,ckmmc::Device &DstDevice, CAdvancedProgress *pProgress) { // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::CopyDisc")); g_pLogDlg->print_line(_T(" Source: [%d,%d,%d] %s"),SrcDevice.address().bus_, SrcDevice.address().target_,SrcDevice.address().lun_, SrcDevice.name()); g_pLogDlg->print_line(_T(" Target: [%d,%d,%d] %s"),DstDevice.address().bus_, DstDevice.address().target_,DstDevice.address().lun_, DstDevice.name()); g_pLogDlg->print_line(_T(" Eject = %d, Simulate = %d, BUP = %d, Pad tracks = %d, Close = %d, Overburn = %d, Swab = %d, Ignore size = %d, Immed = %d, Audio master = %d, Forcespeed = %d, VariRec (enabled) = %d, VariRec (value) = %d, Ignore read errors = %d."), (int)g_BurnImageSettings.m_bEject, (int)g_BurnImageSettings.m_bSimulate, (int)g_BurnImageSettings.m_bBUP, (int)g_BurnImageSettings.m_bPadTracks, (int)g_BurnImageSettings.m_bFixate, (int)g_BurnAdvancedSettings.m_bOverburn, (int)g_BurnAdvancedSettings.m_bSwab, (int)g_BurnAdvancedSettings.m_bIgnoreSize, (int)g_BurnAdvancedSettings.m_bImmed, (int)g_BurnAdvancedSettings.m_bAudioMaster, (int)g_BurnAdvancedSettings.m_bForceSpeed, (int)g_BurnAdvancedSettings.m_bVariRec, g_BurnAdvancedSettings.m_iVariRec, (int)g_ReadSettings.m_bIgnoreErr); } // Initialize this object. Initialize(MODE_BURNIMAGE,pProgress); // Since this function uses a batch file for execution no cygwin paths are included in // stderr messages. m_bErrorPathMode = false; // We need to specify the total size that we should record. m_uiProcessedSize = 0; m_uiTotalSize = g_CopyDiscSettings.m_uiSourceSize / (1024 * 1024); // MB. m_TrackSize.push_back(m_uiTotalSize); std::string CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = CORE_READAPP; CommandLine += " -v dev="; // Source device. CommandLine += NDeviceUtil::GetDeviceAddrA(SrcDevice); // Speed. char szBuffer[64]; if (g_BurnImageSettings.m_iWriteSpeed != -1) { sprintf(szBuffer," speed=%d",g_BurnImageSettings.m_iWriteSpeed); CommandLine += szBuffer; } // Ignore read errors. if (g_ReadSettings.m_bIgnoreErr) CommandLine += " -noerror -nocorr"; // Redirection. CommandLine += " f=- 2> NUL: | "; // Write app related. CommandLine += CORE_WRITEAPP; CommandLine += " -v dev="; CommandLine += NDeviceUtil::GetDeviceAddrA(DstDevice); sprintf(szBuffer," gracetime=%d",g_GlobalSettings.m_iGraceTime); CommandLine += szBuffer; // FIFO. if (g_GlobalSettings.m_iFIFOSize != 4) { sprintf(szBuffer," fs=%dm",g_GlobalSettings.m_iFIFOSize); CommandLine += szBuffer; } // Eject. if (DstDevice.support(ckmmc::Device::ckDEVICE_EJECT) && g_BurnImageSettings.m_bEject) { CommandLine += " -eject"; } // Simulation. if (DstDevice.support(ckmmc::Device::ckDEVICE_TEST_WRITE) && g_BurnImageSettings.m_bSimulate) { CommandLine += " -dummy"; } // Write method. switch (g_BurnImageSettings.m_iWriteMethod) { case WRITEMETHOD_SAO: CommandLine += " -sao"; break; case WRITEMETHOD_TAO: CommandLine += " -tao"; break; case WRITEMETHOD_TAONOPREGAP: CommandLine += " -tao pregap=0"; break; case WRITEMETHOD_RAW96R: CommandLine += " -raw96r"; break; case WRITEMETHOD_RAW16: CommandLine += " -raw16"; break; case WRITEMETHOD_RAW96P: CommandLine += " -raw96p"; break; }; char szDriverOpts[128]; strcpy(szDriverOpts," driveropts="); bool bUseDriverOpts = false; // Buffer underrun protection. if (DstDevice.support(ckmmc::Device::ckDEVICE_BUP)) { bUseDriverOpts = true; if (g_BurnImageSettings.m_bBUP) strcat(szDriverOpts,"burnfree,"); else strcat(szDriverOpts,"noburnfree,"); } // Audio master. if (DstDevice.support(ckmmc::Device::ckDEVICE_AUDIO_MASTER)) { if (g_BurnAdvancedSettings.m_bAudioMaster) { strcat(szDriverOpts,"audiomaster,"); bUseDriverOpts = true; } } // Forcespeed. if (DstDevice.support(ckmmc::Device::ckDEVICE_FORCE_SPEED)) { if (!g_BurnAdvancedSettings.m_bForceSpeed) { strcat(szDriverOpts,"noforcespeed,"); bUseDriverOpts = true; } } // VariRec. if (DstDevice.support(ckmmc::Device::ckDEVICE_VARIREC)) { if (g_BurnAdvancedSettings.m_bVariRec) { char szVariRec[16]; sprintf(szVariRec,"varirec=%d,",g_BurnAdvancedSettings.m_iVariRec); strcat(szDriverOpts,szVariRec); bUseDriverOpts = true; } } if (bUseDriverOpts) { szDriverOpts[strlen(szDriverOpts) - 1] = '\0'; CommandLine += szDriverOpts; } // Pad tracks. if (g_BurnImageSettings.m_bPadTracks) CommandLine += " -pad"; // Fixate. if (!g_BurnImageSettings.m_bFixate) CommandLine += " -nofix"; // Overburning. if (g_BurnAdvancedSettings.m_bOverburn) CommandLine += " -overburn"; // Swap audio byte order. // FIXME: Should probably check for support before selecting. if (g_BurnAdvancedSettings.m_bSwab) CommandLine += " -swab"; // Ignore size. if (g_BurnAdvancedSettings.m_bIgnoreSize) CommandLine += " -ignsize"; // SCSI IMMED flag. if (g_BurnAdvancedSettings.m_bImmed) CommandLine += " -immed"; // Redirection. CommandLine += " -"; char szChangeDir[MAX_PATH + 3]; strcpy(szChangeDir,"cd "); char szFolderPath[MAX_PATH]; UnicodeToAnsi(szFolderPath,g_GlobalSettings.m_szCDRToolsPath,sizeof(szFolderPath)); strcat(szChangeDir,szFolderPath); if (CommandLine.length() > 2047) { // All versions below Windows XP only supports 2047 character command lines (using the shell). if (g_WinVer.m_ulMajorVersion < MAJOR_WINXP || (g_WinVer.m_ulMajorVersion == MAJOR_WINXP && g_WinVer.m_ulMinorVersion < MINOR_WINXP)) { TCHAR szMessage[256]; lsnprintf_s(szMessage,256,lngGetString(ERROR_COMMANDLINE),2048); MessageBox(HWND_DESKTOP,szMessage,lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return false; } // Windows XP supports 8192 character command lines (using the shell). else if (CommandLine.length() > 8191) { TCHAR szMessage[256]; lsnprintf_s(szMessage,256,lngGetString(ERROR_COMMANDLINE),8192); MessageBox(HWND_DESKTOP,szMessage,lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return false; } } // Create the batch file. TCHAR szBatchPath[MAX_PATH]; CreateBatchFile(szChangeDir,CommandLine.c_str(),szBatchPath); TCHAR szBatchCmdLine[MAX_PATH + 2]; lstrcpy(szBatchCmdLine,_T("\"")); lstrcat(szBatchCmdLine,szBatchPath); lstrcat(szBatchCmdLine,_T("\"")); bool bResult = create(szBatchCmdLine); wait(); ckcore::File::remove(szBatchPath); return bResult; } /* CCore::ReadDisc --------------- Reads a disc to a disc image. This function is configured through the g_ReadSettings object. */ bool CCore::ReadDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName, int iMode,bool bWaitForProcess) { m_bOperationRes = false; // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::ReadDisc")); g_pLogDlg->print_line(_T(" File = %s."),szFileName); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); g_pLogDlg->print_line(_T(" Ignore read errors = %d, Clone = %d, Speed = %d."), (int)g_ReadSettings.m_bIgnoreErr, (int)g_ReadSettings.m_bClone, g_ReadSettings.m_iReadSpeed); } // Initialize this object. Initialize(iMode,pProgress); // We need to specify the end adresses (in sectors) that we should read. m_uiProcessedSize = 0; m_uiTotalSize = 0; tstring CommandLine; CommandLine.reserve(MAX_PATH); CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_READAPP); CommandLine += _T("\" dev="); CommandLine += NDeviceUtil::GetDeviceAddr(Device); // Ignore read errors. if (g_ReadSettings.m_bIgnoreErr) CommandLine += _T(" -noerror -nocorr"); // Clone. if (g_ReadSettings.m_bClone) CommandLine += _T(" -clone"); // Speed. if (g_ReadSettings.m_iReadSpeed != -1) { TCHAR szBuffer[64]; lsprintf(szBuffer,_T(" speed=%d"),g_ReadSettings.m_iReadSpeed); // FIXME: Is this CD or profile dependent speed? } // File name. CommandLine += _T(" f=\""); CommandLine += GetCygwinFileName(szFileName); CommandLine += _T("\""); return SafeLaunch(CommandLine,bWaitForProcess); } bool CCore::ReadDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName) { return ReadDisc(Device,pProgress,szFileName,MODE_READDISC,false); } eBurnResult CCore::ReadDiscEx(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName) { if (!ReadDisc(Device,pProgress,szFileName,MODE_READDISCEX,true)) return BURNRESULT_INTERNALERROR; ckcore::tuint32 uiExitCode = 0; exit_code(uiExitCode); return uiExitCode == 0 ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; //return m_bOperationRes ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; } DWORD WINAPI CCore::CreateCompImageThread(LPVOID lpThreadParameter) { CCompImageParams *pParams = (CCompImageParams *)lpThreadParameter; g_Core2.CreateImage(pParams->m_Process,pParams->m_Files, pParams->m_Progress,false); return 0; } DWORD WINAPI CCore::NextCopyThread(LPVOID lpThreadParameter) { CCore *pCore = (CCore *)lpThreadParameter; pCore->Reinitialize(); pCore->m_uiProcessedSize = 0; pCore->m_pProgress->set_progress(0); TCHAR szBuffer[128]; lsprintf(szBuffer,lngGetString(INFO_CREATECOPY), g_BurnImageSettings.m_lNumCopies - pCore->m_lNumCopies + 1, g_BurnImageSettings.m_lNumCopies); pCore->m_pProgress->notify(ckcore::Progress::ckINFORMATION,szBuffer); pCore->SafeLaunch(pCore->m_LastCmdLine,pCore->m_bLastWaitForProcess); return 0; } /* CCore::BurnCompilation ---------------------- Burns a compilation on the fly to a disc. This function is configured through the g_BurnImageSettings and g_ProjectSettings object. */ bool CCore::BurnCompilation(ckmmc::Device &Device,CAdvancedProgress *pProgress, ckcore::Progress &Progress,const ckfilesystem::FileSet &Files, std::vector &AudioTracks,const TCHAR *szAudioText, int iDataMode,unsigned __int64 uiDataBytes,int iMode) { m_bOperationRes = true; // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore::BurnCompilation")); g_pLogDlg->print_line(_T(" [%d,%d,%d] %s"),Device.address().bus_, Device.address().target_,Device.address().lun_, Device.name()); g_pLogDlg->print_line(_T(" Eject = %d, Simulate = %d, BUP = %d, Pad tracks = %d, Close = %d, Overburn = %d, Swab = %d, Ignore size = %d, Immed = %d, Audio master = %d, Forcespeed = %d, VariRec (enabled) = %d, VariRec (value) = %d, Data bytes %I64d."), (int)g_BurnImageSettings.m_bEject, (int)g_BurnImageSettings.m_bSimulate, (int)g_BurnImageSettings.m_bBUP, (int)g_BurnImageSettings.m_bPadTracks, (int)g_BurnImageSettings.m_bFixate, (int)g_BurnAdvancedSettings.m_bOverburn, (int)g_BurnAdvancedSettings.m_bSwab, (int)g_BurnAdvancedSettings.m_bIgnoreSize, (int)g_BurnAdvancedSettings.m_bImmed, (int)g_BurnAdvancedSettings.m_bAudioMaster, (int)g_BurnAdvancedSettings.m_bForceSpeed, (int)g_BurnAdvancedSettings.m_bVariRec, g_BurnAdvancedSettings.m_iVariRec, uiDataBytes); } // Initialize this object. Initialize(iMode,pProgress); // Since this function uses a batch file for execution no cygwin paths are included in // stderr messages. m_bErrorPathMode = false; // We need to specify the total size that we should record. m_uiProcessedSize = 0; m_uiTotalSize = uiDataBytes / (1024 * 1024); // MiB. m_TrackSize.push_back(m_uiTotalSize); for (unsigned int i = 0; i < AudioTracks.size(); i++) { unsigned __int64 uiTrackSize = ckcore::File::size(AudioTracks[i]) / (1024 * 1024); m_TrackSize.push_back(uiTrackSize); m_uiTotalSize += uiTrackSize; } // Setup the command line. tstring CommandLine; CommandLine.reserve(MAX_PATH); // Write application part of the command line. CommandLine = _T("\""); CommandLine += g_GlobalSettings.m_szCDRToolsPath; CommandLine += _T(CORE_WRITEAPP); CommandLine += _T("\" -v dev="); CommandLine += NDeviceUtil::GetDeviceAddr(Device); TCHAR szBuffer[64]; lsprintf(szBuffer,_T(" gracetime=%d"),g_GlobalSettings.m_iGraceTime); CommandLine += szBuffer; // FIFO. if (g_GlobalSettings.m_iFIFOSize != 4) { lsprintf(szBuffer,_T(" fs=%dm"),g_GlobalSettings.m_iFIFOSize); CommandLine += szBuffer; } // Eject. if (Device.support(ckmmc::Device::ckDEVICE_EJECT) && g_BurnImageSettings.m_bEject) { CommandLine += _T(" -eject"); } // Simulation. if (Device.support(ckmmc::Device::ckDEVICE_TEST_WRITE) && g_BurnImageSettings.m_bSimulate) { CommandLine += _T(" -dummy"); } // Write method. switch (g_BurnImageSettings.m_iWriteMethod) { case WRITEMETHOD_SAO: CommandLine += _T(" -sao"); // The SAO method needs to know the size of the file system beforehand (specified in sectors). lsprintf(szBuffer,_T(" tsize=%I64ds"),uiDataBytes/2048); CommandLine += szBuffer; break; case WRITEMETHOD_TAO: CommandLine += _T(" -tao"); break; case WRITEMETHOD_TAONOPREGAP: CommandLine += _T(" -tao pregap=0"); break; case WRITEMETHOD_RAW96R: CommandLine += _T(" -raw96r"); break; case WRITEMETHOD_RAW16: CommandLine += _T(" -raw16"); break; case WRITEMETHOD_RAW96P: CommandLine += _T(" -raw96p"); break; }; TCHAR szDriverOpts[128]; lstrcpy(szDriverOpts,_T(" driveropts=")); bool bUseDriverOpts = false; // Buffer underrun protection. if (Device.support(ckmmc::Device::ckDEVICE_BUP)) { bUseDriverOpts = true; if (g_BurnImageSettings.m_bBUP) lstrcat(szDriverOpts,_T("burnfree,")); else lstrcat(szDriverOpts,_T("noburnfree,")); } // Audio master. if (Device.support(ckmmc::Device::ckDEVICE_AUDIO_MASTER)) { if (g_BurnAdvancedSettings.m_bAudioMaster) { lstrcat(szDriverOpts,_T("audiomaster,")); bUseDriverOpts = true; } } // Forcespeed. if (Device.support(ckmmc::Device::ckDEVICE_FORCE_SPEED)) { if (!g_BurnAdvancedSettings.m_bForceSpeed) { lstrcat(szDriverOpts,_T("noforcespeed,")); bUseDriverOpts = true; } } // VariRec. if (Device.support(ckmmc::Device::ckDEVICE_VARIREC)) { if (g_BurnAdvancedSettings.m_bVariRec) { TCHAR szVariRec[32]; lsprintf(szVariRec,_T("varirec=%d,"),g_BurnAdvancedSettings.m_iVariRec); lstrcat(szDriverOpts,szVariRec); bUseDriverOpts = true; } } if (bUseDriverOpts) { szDriverOpts[lstrlen(szDriverOpts) - 1] = '\0'; CommandLine += szDriverOpts; } // Pad tracks. if (g_BurnImageSettings.m_bPadTracks) CommandLine += _T(" -pad"); // Fixate. if (!g_BurnImageSettings.m_bFixate) CommandLine += _T(" -nofix"); // Overburning. if (g_BurnAdvancedSettings.m_bOverburn) CommandLine += _T(" -overburn"); // Swap audio byte order. // FIXME: Should probably check for support before selecting. if (g_BurnAdvancedSettings.m_bSwab) CommandLine += _T(" -swab"); // Ignore size. if (g_BurnAdvancedSettings.m_bIgnoreSize) CommandLine += _T(" -ignsize"); // SCSI IMMED flag. if (g_BurnAdvancedSettings.m_bImmed) CommandLine += _T(" -immed"); // Speed. if (g_BurnImageSettings.m_iWriteSpeed != -1) { lsprintf(szBuffer,_T(" speed=%d"),g_BurnImageSettings.m_iWriteSpeed); CommandLine += szBuffer; } // Mode. switch (iDataMode) { case 0: // Mode 1 CommandLine += _T(" -data -"); break; case 1: // Mode 2 XA (multisession) CommandLine += _T(" -multi -"); break; }; // Audio tracks. if (AudioTracks.size() > 0) CommandLine += _T(" -audio"); TCHAR szCygwinFileName[MAX_PATH + 16]; for (unsigned int i = 0; i < AudioTracks.size(); i++) { GetCygwinFileName(AudioTracks[i],szCygwinFileName); CommandLine += _T(" \""); CommandLine += szCygwinFileName; CommandLine += _T("\""); } // Audio text. if (szAudioText != NULL) { CommandLine += _T(" textfile=\""); CommandLine += szCygwinFileName; CommandLine += _T("\""); } if (CommandLine.length() > 2047) { // All versions below Windows XP only supports 2047 character command lines (using the shell). if (g_WinVer.m_ulMajorVersion < MAJOR_WINXP || (g_WinVer.m_ulMajorVersion == MAJOR_WINXP && g_WinVer.m_ulMinorVersion < MINOR_WINXP)) { TCHAR szMessage[256]; lsnprintf_s(szMessage,256,lngGetString(ERROR_COMMANDLINE),2048); MessageBox(HWND_DESKTOP,szMessage,lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return false; } // Windows XP supports 8192 character command lines (using the shell). else if (CommandLine.length() > 8191) { TCHAR szMessage[256]; lsnprintf_s(szMessage,256,lngGetString(ERROR_COMMANDLINE),8192); MessageBox(HWND_DESKTOP,szMessage,lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return false; } } // Create a separate thread for writing the file system to the process. CCompImageParams CompImageParams(*this,Progress,Files); unsigned long ulThreadID = 0; HANDLE hThread = ::CreateThread(NULL,0,CreateCompImageThread,&CompImageParams,0,&ulThreadID); ::CloseHandle(hThread); //return Launch((TCHAR *)CommandLine.c_str(),true); return SafeLaunch(CommandLine,true); } bool CCore::BurnCompilation(ckmmc::Device &Device,CAdvancedProgress *pProgress, ckcore::Progress &Progress,const ckfilesystem::FileSet &Files, std::vector &AudioTracks,const TCHAR *szAudioText, int iMode,unsigned __int64 uiDataBytes) { return BurnCompilation(Device,pProgress,Progress,Files,AudioTracks, szAudioText,iMode,uiDataBytes,MODE_BURNIMAGE); } eBurnResult CCore::BurnCompilationEx(ckmmc::Device &Device,CAdvancedProgress *pProgress, ckcore::Progress &Progress,const ckfilesystem::FileSet &Files, std::vector &AudioTracks,const TCHAR *szAudioText, int iMode,unsigned __int64 uiDataBytes) { if (!BurnCompilation(Device,pProgress,Progress,Files,AudioTracks,szAudioText, iMode,uiDataBytes,MODE_BURNIMAGEEX)) { return BURNRESULT_INTERNALERROR; } ckcore::tuint32 uiExitCode = 0; exit_code(uiExitCode); return uiExitCode == 0 ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; //return m_bOperationRes ? BURNRESULT_OK : BURNRESULT_EXTERNALERROR; } ================================================ FILE: src/app/core/core.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include #include #include #include "advanced_progress.hh" #define CORE_IGNORE_ERRORINFOMESSAGES // Should we ignore error information message (copyright etc.)? #define CORE_PRINT_UNSUPERRORMESSAGES // Should we print unhandled/unsupported messages to the log window? #define CORE_DVD_SUPPORT // Is DVD recording supported in this version? enum eBurnResult { BURNRESULT_OK = 0, BURNRESULT_INTERNALERROR = -1, BURNRESULT_EXTERNALERROR = -2 }; #ifdef CDRKIT #define CORE_WRITEAPP "wodim.exe" #define CORE_READAPP "readom.exe" #define CORE_AUDIOAPP "icedax.exe" #else #define CORE_WRITEAPP "cdrecord.exe" #define CORE_READAPP "readcd.exe" #define CORE_AUDIOAPP "cdda2wav.exe" #endif class CCore : public ckcore::Process { private: int m_iMode; int m_iStatusMode; bool m_bGraceTimeDone; bool m_bDummyMode; bool m_bErrorPathMode; // Is set to true when we're expecting a cygwin path in the beginning of each error message. bool m_bOperationRes; unsigned __int64 m_uiProcessedSize; unsigned __int64 m_uiTotalSize; unsigned __int64 m_uiEstimatedSize; // Used when estimating file system size. std::vector m_TrackSize; unsigned int m_uiCurrentTrack; // Holds the length of the path to the cdrtools directory (cygwin path). // This is used to remove the cygwin path to cdrtools on every stderr message. // It's important that the length is updated when the path changes. unsigned int m_uiCDRToolsPathLen; // Object that can receive messages while receiving output from a console // application. CAdvancedProgress *m_pProgress; // Used for creating multiple copies (when recording a disc image). long m_lNumCopies; tstring m_LastCmdLine; bool m_bLastWaitForProcess; // Used when quering version information. ckcore::tstring m_Version; void Initialize(int iMode,CAdvancedProgress *pProgress = NULL); void Reinitialize(); void CreateBatchFile(const char *szChangeDir,const char *szCommandLine,TCHAR *szBatchPath); bool SafeLaunch(tstring &CommandLine,bool bWaitForProcess); bool Relaunch(); bool CheckGraceTime(const char *szBuffer); bool CheckProgress(const char *szBuffer); void ErrorOutputCDRECORD(const char *szBuffer); void ErrorOutputREADCD(const char *szBuffer); void ErrorOutputCDDA2WAV(const char *szBuffer); void EraseOutput(const char *szBuffer); void FixateOutput(const char *szBuffer); void BurnImageOutput(const char *szBuffer); void ReadDataTrackOutput(const char *szBuffer); void ReadAudioTrackOutput(const char *szBuffer); void ScanTrackOutput(const char *szBuffer); void ReadDiscOutput(const char *szBuffer); void VersionOutput(const char *szBuffer); // Inherited events. void event_output(const std::string &block); void event_finished(); // Thread functions. class CCompImageParams // A pointer to a structure of this type should be passed as thead parameter for CreateCompImageThread. { public: ckcore::Process &m_Process; ckcore::Progress &m_Progress; const ckfilesystem::FileSet &m_Files; CCompImageParams(ckcore::Process &Process,ckcore::Progress &Progress, const ckfilesystem::FileSet &Files) : m_Process(Process), m_Progress(Progress),m_Files(Files) { } }; static DWORD WINAPI CreateCompImageThread(LPVOID lpThreadParameter); static DWORD WINAPI NextCopyThread(LPVOID lpThreadParameter); bool BurnImage(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,bool bWaitForProcess,bool bCloneMode); bool BurnTracks(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szDataTrack,std::vector &AudioTracks, const TCHAR *szAudioText,int iDataMode,int iMode,bool bWaitForProcess); bool ReadDataTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName, unsigned int uiTrackNumber,unsigned long ulStartSector,unsigned long ulEndSector, int iMode,bool bWaitForProcess); bool ReadAudioTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName, unsigned int uiTrackNumber,int iMode,bool bWaitForProcess); bool ScanTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress,unsigned int uiTrackNumber, unsigned long ulStartSector,unsigned long ulEndSector,int iMode,bool bWaitForProcess); bool ReadDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName, int iMode,bool bWaitForProcess); bool BurnCompilation(ckmmc::Device &Device,CAdvancedProgress *pProgress, ckcore::Progress &Progress,const ckfilesystem::FileSet &Files, std::vector &AudioTracks,const TCHAR *szAudioText,int iDataMode, unsigned __int64 uiDataBytes,int iMode); enum eMode { MODE_EJECT = 0, MODE_ERASE, MODE_FIXATE, MODE_BURNIMAGE, MODE_BURNIMAGEEX, MODE_READDATATRACK, MODE_READDATATRACKEX, MODE_READAUDIOTRACK, MODE_READAUDIOTRACKEX, MODE_SCANTRACK, MODE_SCANTRACKEX, MODE_READDISC, MODE_READDISCEX, MODE_VERSION }; enum eStatusMode { SMODE_DEFAULT = 0, SMODE_GRACETIME, SMODE_PREPROGRESS, SMODE_PROGRESS, SMODE_AUDIOPROGRESS }; public: CCore(); ~CCore(); bool EjectDisc(ckmmc::Device &Device,bool bWaitForProcess); bool LoadDisc(ckmmc::Device &Device,bool bWaitForProcess); bool EraseDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress, int iMode,bool bForce,bool bEject,bool bSimulate); bool FixateDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress, bool bEject,bool bSimulate); bool BurnImage(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,bool bCloneMode); bool BurnImageEx(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szFileName,bool bCloneMode); bool BurnTracks(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szDataTrack,std::vector &AudioTracks, const TCHAR *szAudioText,int iDataMode); eBurnResult BurnTracksEx(ckmmc::Device &Device,CAdvancedProgress *pProgress, const TCHAR *szDataTrack,std::vector &AudioTracks, const TCHAR *szAudioText,int iDataMode); bool ReadDataTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName, unsigned int uiTrackNumber,unsigned long ulStartSector,unsigned long ulEndSector); eBurnResult ReadDataTrackEx(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName, unsigned int uiTrackNumber,unsigned long ulStartSector,unsigned long ulEndSector); bool ReadAudioTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName, unsigned int uiTrackNumber); eBurnResult ReadAudioTrackEx(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName, unsigned int uiTrackNumber); bool ScanTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress,unsigned int uiTrackNumber, unsigned long ulStartSector,unsigned long ulEndSector); eBurnResult ScanTrackEx(ckmmc::Device &Device,CAdvancedProgress *pProgress,unsigned int uiTrackNumber, unsigned long ulStartSector,unsigned long ulEndSector); bool CopyDisc(ckmmc::Device &SrcDevice,ckmmc::Device &DstDevice,CAdvancedProgress *pProgress); bool ReadDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName); eBurnResult ReadDiscEx(ckmmc::Device &Device,CAdvancedProgress *pProgress,const TCHAR *szFileName); bool BurnCompilation(ckmmc::Device &Device,CAdvancedProgress *pProgress, ckcore::Progress &Progress,const ckfilesystem::FileSet &Files,std::vector &AudioTracks, const TCHAR *szAudioText,int iMode,unsigned __int64 uiDataBytes); eBurnResult BurnCompilationEx(ckmmc::Device &Device,CAdvancedProgress *pProgress,ckcore::Progress &Progress, const ckfilesystem::FileSet &Files,std::vector &AudioTracks, const TCHAR *szAudioText,int iMode,unsigned __int64 uiDataBytes); ckcore::tstring CdrtoolsVersion(); }; extern CCore g_Core; ================================================ FILE: src/app/core/core2.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include #include #include #include "core2.hh" #include "core2_Format.hh" #include "core2_blank.hh" #include "core2_util.hh" #include "core2_info.hh" #include "core2_read.hh" #include "log_dlg.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" CCore2 g_Core2; CCore2::CCore2() { } CCore2::~CCore2() { } bool CCore2::HandleEvents(ckmmc::Device &Device,CAdvancedProgress *pProgress, unsigned char &ucHandledEvents) { ucHandledEvents = 0; unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); // Handle events. unsigned char ucEvents = 0xFF; unsigned char ucEvent[8]; unsigned char ucStartCount = 0; while (ucEvents) { ucCdb[0] = SCSI_GET_EVENT_STATUS_NOTIFICATION; ucCdb[1] = 0x01; // Polled. ucCdb[4] = ucEvents; ucCdb[8] = sizeof(ucEvent); ucCdb[9] = 0x00; if (!Device.transport(ucCdb,10,ucEvent,sizeof(ucEvent),ckmmc::Device::ckTM_READ)) return false; ucEvents = ucEvent[3]; if ((ucEvent[2] & 0x07) == 0 || (ucEvent[0] << 8 | ucEvent[1]) == 2 || (ucEvent[4] & 0x0F) == 0) // No Changes return true; unsigned int uiDescriptor = ucEvent[4] << 24 | ucEvent[5] << 16 | ucEvent[6] << 8 | ucEvent[7]; switch (ucEvent[2] & 0x07) { case 0: // No reqeusted event classes are supported. return true; case 1: // Operational change request/notification. ucHandledEvents |= 0x01; break; case 2: // Power management. if ((uiDescriptor & 0xFF0000) != 0x01) { // For some reasons this code is not compatible with all recorders. if (ucStartCount == 10) { g_pLogDlg->print_line(_T(" Warning: Unable to start the drive, aborting after %d retries."),ucStartCount); return true; } g_pLogDlg->print_line(_T(" The drive is not in active state.")); if (!StartStopUnit(Device,LOADMEDIA_START,false)) { if (pProgress != NULL) pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_NOMEDIA)); return false; } g_pLogDlg->print_line(_T(" -> Started the disc to make it ready for access.")); ucStartCount++; } ucHandledEvents |= 0x02; break; case 3: // External request. ucHandledEvents |= 0x04; break; case 4: // Media. ucHandledEvents |= 0x08; break; case 5: // Multiple hosts. ucHandledEvents |= 0x10; break; case 6: // Device busy. ucHandledEvents |= 0x20; break; case 7: // Reserved. ucHandledEvents |= 0x40; break; } } return true; } bool CCore2::WaitForUnit(ckmmc::Device &Device,CAdvancedProgress *pProgress) { // Initialize buffers. unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); unsigned char ucSense[24]; memset(ucSense,0,sizeof(ucSense)); // Prepare command. ucCdb[0] = SCSI_TEST_UNIT_READY; while (true) { Sleep(1000); unsigned char ucResult; if (!Device.transport_with_sense(ucCdb,6,NULL,0,ckmmc::Device::ckTM_READ, ucSense,ucResult)) { return false; } // Check if we're done. if (ucResult == SCSISTAT_GOOD) return true; // Check for errors. /*switch (ucSense[2] & 0x0F) { case SENSEKEY_MEDIUM_ERROR: case SENSEKEY_HARDWARE_ERROR: return false; case SENSEKEY_NOT_READY: break; }*/ // See if we're formating a disc. unsigned char ucCode = CheckSense(ucSense); if (ucCode == SENSE_FORMATINPROGRESS || ucCode == SENSE_LONGWRITEINPROGRESS) { // Check if the operation has been cancelled. if (pProgress != NULL && pProgress->cancelled()) { // Stop the unit and unlock the media. CloseTrackSession(Device,0,0,true); LockMedia(Device,false); return false; } // Update the progress. if (pProgress != NULL) { // If the SKSV bit is set to zero we are done. if (ucSense[15] & 0x80) { unsigned short usProgress = ((unsigned short)ucSense[16] << 8) | ucSense[17]; pProgress->set_progress((unsigned char)(usProgress * 100.0f / 0xFFFF)); } else { pProgress->set_progress(100); return true; } } } } return true; } CCore2::eMediaChange CCore2::CheckMediaChange(ckmmc::Device &Device) { unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); // Handle events. unsigned char ucEvent[8]; ucCdb[0] = SCSI_GET_EVENT_STATUS_NOTIFICATION; ucCdb[1] = 0x01; // Polled. ucCdb[4] = 0x10; ucCdb[8] = sizeof(ucEvent); ucCdb[9] = 0x00; if (!Device.transport(ucCdb,10,ucEvent,sizeof(ucEvent), ckmmc::Device::ckTM_READ)) { return MEDIACHANGE_NOCHANGE; } unsigned char ucEventCode = ucEvent[4] & 0x0F; switch (ucEventCode) { case 1: Device.refresh(); return MEDIACHANGE_EJECTREQUEST; case 2: Device.refresh(); return MEDIACHANGE_NEWMEDIA; case 3: Device.refresh(); return MEDIACHANGE_MEDIAREMOVAL; case 4: Device.refresh(); return MEDIACHANGE_MEDIACHANGED; case 5: Device.refresh(); return MEDIACHANGE_BGFORMAT_COMPLETED; case 6: Device.refresh(); return MEDIACHANGE_BGFORMAT_RESTARTED; } return MEDIACHANGE_NOCHANGE; } bool CCore2::LockMedia(ckmmc::Device &Device,bool bLock) { // Initialize buffers. unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[0] = SCSI_PREVENTALLOW_MEDIUM_REMOVAL; ucCdb[4] = (unsigned char)bLock; ucCdb[5] = 0x00; if (!Device.transport(ucCdb,6,NULL,0,ckmmc::Device::ckTM_READ)) return false; return true; } bool CCore2::StartStopUnit(ckmmc::Device &Device,eLoadMedia Action,bool bImmed) { // Initialize buffers. unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); unsigned char ucSense[24]; memset(ucSense,0,sizeof(ucSense)); ucCdb[0] = SCSI_START_STOP_UNIT; ucCdb[1] = (unsigned char)bImmed; ucCdb[4] = (unsigned char)Action; ucCdb[5] = 0x00; unsigned char ucResult = 0; if (!Device.transport_with_sense(ucCdb,6,NULL,0,ckmmc::Device::ckTM_READ, ucSense,ucResult)) { return false; } if (ucResult != SCSISTAT_GOOD) { if ((ucSense[2] & 0x0F) == SENSEKEY_NOT_READY) { if (ucSense[12] == 0x3A) { switch (ucSense[13]) { case 0x00: // MEDIUM NOT PRESENT case 0x01: // MEDIUM NOT PRESENT TRAY CLOSED. break; case 0x02: // MEDIUM NOT PRESENT TRAY OPEN if (Action != LOADMEDIA_LOAD) { g_pLogDlg->print_line(_T(" Warning: Unable to start media, trying to manually load it.")); return StartStopUnit(Device,LOADMEDIA_LOAD,bImmed); } break; } } } g_pLogDlg->print_line(_T(" Error: Could not start or stop the unit.")); // Dump CDB. g_pLogDlg->print(_T(" CDB:\t")); for (unsigned int i = 0; i < 6; i++) { if (i == 0) g_pLogDlg->print(_T("0x%.2X"),ucCdb[i]); else g_pLogDlg->print(_T(",0x%.2X"),ucCdb[i]); } g_pLogDlg->print_line(_T("")); // Dump sense information. g_pLogDlg->print_line(_T(" Sense:\t0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X"), ucSense[0],ucSense[1],ucSense[2],ucSense[3], ucSense[4],ucSense[5],ucSense[6],ucSense[7]); g_pLogDlg->print_line(_T(" \t0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X"), ucSense[ 8],ucSense[ 9],ucSense[10],ucSense[11], ucSense[12],ucSense[13],ucSense[14],ucSense[15]); g_pLogDlg->print_line(_T(" \t0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X,0x%.2X"), ucSense[16],ucSense[17],ucSense[18],ucSense[19], ucSense[20],ucSense[21],ucSense[22],ucSense[23]); return false; } return true; } bool CCore2::CloseTrackSession(ckmmc::Device &Device,unsigned char ucCloseFunction, unsigned short usTrackNumber,bool bImmed) { if (ucCloseFunction > 0x07) return false; // Initialize buffers. unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[0] = SCSI_CLOSE_TRACK_SESSION; ucCdb[1] = bImmed ? 0x01 : 0x00; ucCdb[2] = ucCloseFunction & 0x07; ucCdb[4] = static_cast(usTrackNumber >> 8); ucCdb[5] = static_cast(usTrackNumber & 0xFF); ucCdb[9] = 0x00; if (!Device.transport(ucCdb,10,NULL,0,ckmmc::Device::ckTM_READ)) return false; return true; } bool CCore2::SetDiscSpeeds(ckmmc::Device &Device,unsigned short usReadSpeed, unsigned short usWriteSpeed) { // Initialize buffers. unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[ 0] = SCSI_SET_CD_SPEED; ucCdb[ 2] = static_cast(usReadSpeed >> 8); ucCdb[ 3] = static_cast(usReadSpeed & 0xFF); ucCdb[ 4] = static_cast(usWriteSpeed >> 8); ucCdb[ 5] = static_cast(usWriteSpeed & 0xFF); ucCdb[11] = 0x08; if (!Device.transport(ucCdb,12,NULL,0,ckmmc::Device::ckTM_READ)) return false; return true; } /** Updates mode page 5 of the specified device. @param pDevice the device to update. @param bTestWrite specifies wether the drive should test write or not. @param WriteMode specifies the write mode to use for recording. @param bSilent if true, the function will not output any error to the log if it failed. @return true if the mode page was successfully updated, false otherwise. */ bool CCore2::UpdateModePage5(ckmmc::Device &Device,bool bTestWrite, bool bSilent) { // Initialize buffers. unsigned char ucBuffer[128]; memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); // Read the current code page information. ucCdb[0] = SCSI_MODE_SENSE10; ucCdb[2] = 0x05; // Default values and code page. ucCdb[7] = sizeof(ucBuffer) >> 8; // Allocation length (MSB). ucCdb[8] = sizeof(ucBuffer) & 0xFF; // Allocation length (LSB). ucCdb[9] = 0x00; if (!Device.transport(ucCdb,10,ucBuffer,sizeof(ucBuffer), ckmmc::Device::ckTM_READ)) { return false; } if ((ucBuffer[8] & 0x3F) != 0x05) return false; // Change the code page. //ucBuffer[8 + 2] |= bTestWrite ? 0x10 : 0x00; if (bTestWrite) ucBuffer[8 + 2] |= 0x10; else ucBuffer[8 + 2] &= ~0x10; // Send the updated code page. unsigned short usFileListSize = (ucBuffer[0] << 8 | ucBuffer[1]) + 2; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[0] = SCSI_MODE_SELECT10; ucCdb[1] = 0x10; // PF (not using vendor specified mode page). ucCdb[7] = static_cast(usFileListSize >> 8); ucCdb[8] = static_cast(usFileListSize & 0xFF); ucCdb[9] = 0x00; if (!bSilent) { if (!Device.transport(ucCdb,10,ucBuffer,usFileListSize, ckmmc::Device::ckTM_WRITE)) { return false; } } else { unsigned char ucSense[24]; memset(ucSense,0,sizeof(ucSense)); unsigned char ucResult = 0; if (!Device.transport_with_sense(ucCdb,10,ucBuffer,usFileListSize, ckmmc::Device::ckTM_WRITE,ucSense,ucResult)) { return false; } if (ucResult != SCSISTAT_GOOD) return false; } return true; } bool CCore2::EraseDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress, int iMethod,bool bForce,bool bEject,bool bSimulate, unsigned int uiSpeed) { // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore2::EraseDisc")); TCHAR szParameters[128]; lsprintf(szParameters,_T(" Method = %d, Force = %d, Eject = %d, Simulate = %d."), iMethod,(int)bForce,(int)bEject,(int)bSimulate); g_pLogDlg->print_line(szParameters); } // Setup the progress dialog. pProgress->AllowCancel(false); pProgress->SetRealMode(!bSimulate); // Turn test writing on if selected. if (!UpdateModePage5(Device,bSimulate)) g_pLogDlg->print_line(_T(" Warning: Unable to update code page 0x05.")); // Disabled until these routines are concidered stable enough. #if 0 // Lock the media. if (!LockMedia(pDevice,true)) g_pLogDlg->print_line(_T(" Warning: Unable to lock device media.")); #endif // Set write speed. if (!SetDiscSpeeds(Device,0xFFFF,(unsigned short)uiSpeed)) g_pLogDlg->print_line(_T(" Warning: Unable to set disc erase speed.")); bool bResult = false; switch (iMethod) { case ERASE_FORMAT_QUICK: case ERASE_FORMAT_FULL: { CCore2Format Core2Format; bResult = Core2Format.FormatUnit(Device,pProgress,iMethod == ERASE_FORMAT_FULL); } break; case ERASE_BLANK_FULL: case ERASE_BLANK_MINIMAL: case ERASE_BLANK_UNCLOSE: case ERASE_BLANK_SESSION: { CCore2Blank Core2Blank; bResult = Core2Blank.Blank(Device,pProgress,iMethod,bForce,bSimulate); } break; } // Unlock the media. if (!LockMedia(Device,false)) g_pLogDlg->print_line(_T(" Warning: Unable to unlock device media.")); // Eject the media (if requested). if (bResult && bEject) { if (!StartStopUnit(Device,LOADMEDIA_EJECT,true)) g_pLogDlg->print_line(_T(" Warning: Unable to eject media.")); } return bResult; } bool CCore2::ReadDataTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress, unsigned char ucTrackNumber,bool bIgnoreErr,const TCHAR *szFilePath) { // Initialize log. if (g_GlobalSettings.m_bLog) { g_pLogDlg->print_line(_T("CCore2::ReadTrack")); TCHAR szParameters[128]; lsprintf(szParameters,_T(" Track = %d."),ucTrackNumber); g_pLogDlg->print_line(szParameters); } CCore2Info Info; CCore2Read Read; // Print the maximum read speed (for diagnostics purposes). ckcore::tuint32 uiMaxReadSpeed = Device.property(ckmmc::Device::ckPROP_MAX_READ_SPD); g_pLogDlg->print_line(_T(" Maximum read speed: %d KiB/s."),uiMaxReadSpeed); if (!SetDiscSpeeds(Device,0xFFFF,0xFFFF)) g_pLogDlg->print_line(_T(" Warning: Unable to set the device read speed.")); unsigned char ucFirstTrackNumber = 0,ucLastTrackNumber = 0; std::vector Tracks; if (Info.ReadTOC(Device,ucFirstTrackNumber,ucLastTrackNumber,Tracks)) { g_pLogDlg->print_line(_T(" First and last disc track number: %d, %d."), ucFirstTrackNumber,ucLastTrackNumber); // Validate the requested track number. if (ucFirstTrackNumber > ucTrackNumber || ucLastTrackNumber < ucTrackNumber) { g_pLogDlg->print_line(_T(" Error: The requested track number is invalid.")); return false; } } else { g_pLogDlg->print_line(_T(" Error: Unable to read TOC information to validate selected track.")); return false; } // Obtain track start address. unsigned long ulTrackAddr = Tracks[ucTrackNumber - 1].m_ulTrackAddr; CCore2TrackInfo TrackInfo; if (!Info.ReadTrackInformation(Device,CCore2Info::TIT_LBA,ulTrackAddr,&TrackInfo)) { g_pLogDlg->print_line(_T(" Error: Unable to read track information.")); return false; } unsigned long ulTrackSize = TrackInfo.m_ulTrackSize; // Always assume a post-gap of 150 sectors. This may be a bad idea. ulTrackSize -= 150; g_pLogDlg->print_line(_T(" Track span: %d-%d."),ulTrackAddr,ulTrackAddr + ulTrackSize); unsigned long ulMin = (ulTrackSize + 150)/(60*75); unsigned long ulSec = (ulTrackSize + 150 - ulMin * 60 * 75)/75; unsigned long ulFrame = ulTrackSize + 150 - ulMin * 60 * 75 - ulSec * 75; g_pLogDlg->print_line(_T(" Track length: %02d:%02d:%02d"),ulMin,ulSec,ulFrame); pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINREADTRACK),ucTrackNumber); pProgress->set_status(lngGetString(STATUS_READTRACK)); #ifdef DEBUG g_pLogDlg->print_line(_T(" Tracks (start, length):")); std::vector::const_iterator it; for (it = Tracks.begin(); it != Tracks.end(); it++) { CCore2TrackInfo TrackInfo; if (Info.ReadTrackInformation(Device,CCore2Info::TIT_LBA,(*it).m_ulTrackAddr,&TrackInfo)) { unsigned long ulMin = (TrackInfo.m_ulTrackSize + 150)/(60*75); unsigned long ulSec = (TrackInfo.m_ulTrackSize + 150 - ulMin * 60 * 75)/75; unsigned long ulFrame = TrackInfo.m_ulTrackSize + 150 - ulMin * 60 * 75 - ulSec * 75; g_pLogDlg->print_line(_T(" %d, %02d:%02d:%02d (%d)"),(*it).m_ulTrackAddr,ulMin,ulSec,ulFrame,TrackInfo.m_ulTrackSize); } } #endif ckcore::FileOutStream OutStream(szFilePath); if (!OutStream.open()) { g_pLogDlg->print_line(_T(" Error: Unable to open the output file: \"%s\"."),szFilePath); return false; } Core2ReadFunction::CReadUserData ReadFunc(Device,&OutStream); // Start reading the selected sectors from the disc. bool bResult = Read.ReadData(Device,pProgress,&ReadFunc,ulTrackAddr,ulTrackSize,bIgnoreErr); OutStream.close(); if (bResult) pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_READTRACK),ucTrackNumber); return bResult; } /* CCore2::ReadFullTOC ------------------- Reads the full TOC and saves the data into a cdrtools compatible file. */ bool CCore2::ReadFullTOC(ckmmc::Device &Device,const TCHAR *szFileName) { // Initialize buffers. unsigned char ucBuffer[4 + 2048]; // It feels stupid to allocate this much memory when // only 2 bytes of data is needed. The problem is that // some drives (tested with TSSTCorp CD/DVDW SH-S183A SB00) // returns more data then requested which may cause buffer // overruns. memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[0] = SCSI_READ_TOC_PMA_ATIP; ucCdb[2] = 0x02; // Full Q sub-code data. ucCdb[7] = sizeof(ucBuffer) >> 8; // Allocation length (MSB). ucCdb[8] = sizeof(ucBuffer) & 0xFF; // Allocation length (LSB). ucCdb[9] = 0; if (!Device.transport(ucCdb,10,ucBuffer,sizeof(ucBuffer), ckmmc::Device::ckTM_READ)) { return false; } // Save the data to the specified file name. ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_WRITE)) { g_pLogDlg->print_line(_T(" Error: Unable to open file \"%s\" for writing."),szFileName); return false; } unsigned short usDataLen = ((unsigned short)ucBuffer[0] << 8) | ucBuffer[1]; if (File.write(ucBuffer,usDataLen + 2) == -1) { g_pLogDlg->print_line(_T(" Error: Unable to write to file \"%s\"."),szFileName); return false; } return true; } int CCore2::CreateImage(ckcore::OutStream &OutStream,const ckfilesystem::FileSet &Files, ckcore::Progress &Progress,bool bFailOnError, std::map *pFilePathMap) { ckfilesystem::FileSystem::Type FileSysType; switch (g_ProjectSettings.m_iFileSystem) { case FILESYSTEM_ISO: FileSysType = g_ProjectSettings.m_bJoliet ? ckfilesystem::FileSystem::TYPE_ISO_JOLIET : ckfilesystem::FileSystem::TYPE_ISO; break; case FILESYSTEM_ISO_UDF: FileSysType = g_ProjectSettings.m_bJoliet ? ckfilesystem::FileSystem::TYPE_ISO_UDF_JOLIET : ckfilesystem::FileSystem::TYPE_ISO_UDF; break; case FILESYSTEM_DVDVIDEO: FileSysType = ckfilesystem::FileSystem::TYPE_DVDVIDEO; break; case FILESYSTEM_UDF: FileSysType = ckfilesystem::FileSystem::TYPE_UDF; break; default: ATLASSERT(false); ckcore::throw_internal_error(_T(__FILE__),__LINE__); } ckfilesystem::Iso::InterchangeLevel InterchangeLevel; switch (g_ProjectSettings.m_iIsoLevel) { case 0: InterchangeLevel = ckfilesystem::Iso::LEVEL_1; break; case 1: InterchangeLevel = ckfilesystem::Iso::LEVEL_2; break; case 2: InterchangeLevel = ckfilesystem::Iso::LEVEL_3; break; case 3: InterchangeLevel = ckfilesystem::Iso::ISO9660_1999; break; default: ATLASSERT(false); ckcore::throw_internal_error(_T(__FILE__),__LINE__); } ckfilesystem::CharacterSet CharacterSet = ckfilesystem::CHARSET_ISO; switch (g_ProjectSettings.m_IsoCharSet) { case CProjectSettings::CHARSET_ISO: CharacterSet = ckfilesystem::CHARSET_ISO; break; case CProjectSettings::CHARSET_DOS: CharacterSet = ckfilesystem::CHARSET_DOS; break; case CProjectSettings::CHARSET_ASCII: CharacterSet = ckfilesystem::CHARSET_ASCII; break; default: assert(false); break; } ckfilesystem::FileSystem FileSys(FileSysType,Files); FileSys.set_long_joliet_names(g_ProjectSettings.m_bJolietLongNames); FileSys.set_interchange_level(InterchangeLevel); FileSys.set_char_set(CharacterSet); FileSys.set_include_file_ver_info(!g_ProjectSettings.m_bOmitVerNum); FileSys.set_relax_max_dir_level(g_ProjectSettings.m_bDeepDirs); FileSys.set_volume_label(g_ProjectSettings.m_szLabel); FileSys.set_text_fields(g_ProjectSettings.m_szSystem, g_ProjectSettings.m_szVolumeSet,g_ProjectSettings.m_szPublisher, g_ProjectSettings.m_szPreparer); FileSys.set_file_fields(g_ProjectSettings.m_szCopyright, g_ProjectSettings.m_szAbstract,g_ProjectSettings.m_szBibliographic); std::list::const_iterator itBootImage; for (itBootImage = g_ProjectSettings.m_BootImages.begin(); itBootImage != g_ProjectSettings.m_BootImages.end(); itBootImage++) { switch ((*itBootImage)->m_iEmulation) { case PROJECTBI_BOOTEMU_NONE: FileSys.add_boot_image_no_emu((*itBootImage)->m_FullPath.c_str(), !(*itBootImage)->m_bNoBoot,(*itBootImage)->m_uiLoadSegment,(*itBootImage)->m_uiLoadSize); break; case PROJECTBI_BOOTEMU_FLOPPY: FileSys.add_boot_image_floppy((*itBootImage)->m_FullPath.c_str(), !(*itBootImage)->m_bNoBoot); break; case PROJECTBI_BOOTEMU_HARDDISK: FileSys.add_boot_image_hard_disk((*itBootImage)->m_FullPath.c_str(), !(*itBootImage)->m_bNoBoot); break; } } unsigned long ulSectorOffset = 0; if (g_ProjectSettings.m_bMultiSession) ulSectorOffset = (unsigned long)g_ProjectSettings.m_uiNextWritableAddr; ckfilesystem::FileSystemWriter FileSysWriter(*g_pLogDlg,FileSys,bFailOnError); int iResult = FileSysWriter.write(OutStream,Progress,ulSectorOffset); if (pFilePathMap != NULL) FileSysWriter.file_path_map(*pFilePathMap); return iResult; } /* A wrapper method for the function above. */ int CCore2::CreateImage(const TCHAR *szFullPath,const ckfilesystem::FileSet &Files, ckcore::Progress &Progress,bool bFailOnError, std::map *pFilePathMap) { ckcore::FileOutStream FileStream(szFullPath); if (!FileStream.open()) { g_pLogDlg->print_line(_T(" Error: Unable to obtain file handle to \"%s\"."),szFullPath); return RESULT_FAIL; } return CreateImage(FileStream,Files,Progress,bFailOnError,pFilePathMap); } int CCore2::EstimateImageSize(const ckfilesystem::FileSet &Files,ckcore::Progress &Progress, unsigned __int64 &uiImageSize) { ckcore::NullStream OutStream; int iResult = CreateImage(OutStream,Files,Progress,true); uiImageSize = OutStream.written(); return iResult; } ================================================ FILE: src/app/core/core2.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include #include #include #include #include #include "scsi.hh" #include "advanced_progress.hh" class CCore2 { public: CCore2(); ~CCore2(); enum eLoadMedia { LOADMEDIA_STOP = 0x00, LOADMEDIA_START = 0x01, LOADMEDIA_EJECT = 0x02, LOADMEDIA_LOAD = 0x03 }; enum eMediaChange { MEDIACHANGE_NOCHANGE, MEDIACHANGE_EJECTREQUEST, MEDIACHANGE_NEWMEDIA, MEDIACHANGE_MEDIAREMOVAL, MEDIACHANGE_MEDIACHANGED, MEDIACHANGE_BGFORMAT_COMPLETED, MEDIACHANGE_BGFORMAT_RESTARTED }; enum { ERASE_FORMAT_QUICK, ERASE_FORMAT_FULL, ERASE_BLANK_FULL, ERASE_BLANK_MINIMAL, ERASE_BLANK_UNCLOSE, ERASE_BLANK_SESSION }; bool HandleEvents(ckmmc::Device &Device,CAdvancedProgress *pProgress, unsigned char &ucHandledEvents); bool WaitForUnit(ckmmc::Device &Device,CAdvancedProgress *pProgress); eMediaChange CheckMediaChange(ckmmc::Device &Device); bool LockMedia(ckmmc::Device &Device,bool bLock); bool StartStopUnit(ckmmc::Device &Device,eLoadMedia Action,bool bImmed); bool CloseTrackSession(ckmmc::Device &Device,unsigned char ucCloseFunction, unsigned short usTrackNumber,bool bImmed); bool SetDiscSpeeds(ckmmc::Device &Device,unsigned short usReadSpeed, unsigned short usWriteSpeed); bool UpdateModePage5(ckmmc::Device &Device,bool bTestWrite,bool bSilent = false); // Primary functions. bool EraseDisc(ckmmc::Device &Device,CAdvancedProgress *pProgress,int iMethod, bool bForce,bool bEject,bool bSimulate,unsigned int uiSpeed); bool ReadDataTrack(ckmmc::Device &Device,CAdvancedProgress *pProgress, unsigned char ucTrackNumber,bool bIgnoreErr,const TCHAR *szFilePath); bool ReadFullTOC(ckmmc::Device &Device,const TCHAR *szFileName); int CreateImage(ckcore::OutStream &OutStream,const ckfilesystem::FileSet &Files, ckcore::Progress &Progress,bool bFailOnError, std::map *pFilePathMap = NULL); int CreateImage(const TCHAR *szFullPath,const ckfilesystem::FileSet &Files, // Wrapper. ckcore::Progress &Progress,bool bFailOnError, std::map *pFilePathMap = NULL); int EstimateImageSize(const ckfilesystem::FileSet &Files,ckcore::Progress &Progress, // Wrapper. unsigned __int64 &uiImageSize); }; extern CCore2 g_Core2; ================================================ FILE: src/app/core/core2_blank.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "core2_blank.hh" #include "core2.hh" #include "log_dlg.hh" #include "string_table.hh" #include "lang_util.hh" CCore2Blank::CCore2Blank() { } CCore2Blank::~CCore2Blank() { } bool CCore2Blank::Blank(ckmmc::Device &Device,CAdvancedProgress *pProgress, int iMethod,bool bForce,bool bSimulate) { g_pLogDlg->print_line(_T("CCore2Blank::Blank")); unsigned char ucBlankType; switch (iMethod) { case CCore2::ERASE_BLANK_FULL: ucBlankType = 0x00; break; case CCore2::ERASE_BLANK_MINIMAL: ucBlankType = 0x01; break; case CCore2::ERASE_BLANK_UNCLOSE: ucBlankType = 0x05; break; case CCore2::ERASE_BLANK_SESSION: ucBlankType = 0x06; break; default: g_pLogDlg->print_line(_T(" Warning: Unknown erase method, using full erase.")); ucBlankType = 0x00; break; } // Initialize buffers. unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); // Handle any unhandled events. unsigned char ucEvents; if (g_Core2.HandleEvents(Device,pProgress,ucEvents)) { g_pLogDlg->print_line(_T(" Handled events: 0x%.2X"),ucEvents); } else { g_pLogDlg->print_line(_T(" Error: Failed to handle events, handled events: 0x%.2X"),ucEvents); return false; } // Start the smoke. if (!bSimulate) pProgress->StartSmoke(); // Execute the blank command. memset(ucCdb,0,16); ucCdb[ 0] = SCSI_BLANK; ucCdb[ 1] = 0x10 | ucBlankType; // Immed and blank type. ucCdb[11] = 0x00; pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINERASE),bSimulate ? lngGetString(WRITEMODE_SIMULATION) : lngGetString(WRITEMODE_REAL)); pProgress->set_status(lngGetString(STATUS_ERASE)); // Worst case scenario if the immed flag has no effect (DVD-RW DL at 1x). Device.timeout(60 * 120); if (!Device.transport(ucCdb,12,NULL,0,ckmmc::Device::ckTM_READ)) { Device.timeout(60); pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_ERASE)); return false; } Device.timeout(60); if (!g_Core2.WaitForUnit(Device,pProgress)) return false; pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_ERASE)); return true; } ================================================ FILE: src/app/core/core2_blank.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "advanced_progress.hh" class CCore2Blank { public: CCore2Blank(); ~CCore2Blank(); bool Blank(ckmmc::Device &Device,CAdvancedProgress *pProgress, int iMethod,bool bForce,bool bSimulate); }; ================================================ FILE: src/app/core/core2_format.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "core2_Format.hh" #include "core2.hh" #include "core2_util.hh" #include "log_dlg.hh" #include "string_table.hh" #include "lang_util.hh" CCore2Format::CCore2Format() { } CCore2Format::~CCore2Format() { } bool CCore2Format::WaitBkgndFormat(ckmmc::Device &Device,CAdvancedProgress *pProgress) { // Initialize buffers. unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); unsigned char ucSense[24]; memset(ucSense,0,sizeof(ucSense)); // Prepare command. ucCdb[0] = SCSI_REQUEST_SENSE; ucCdb[4] = sizeof(ucSense); ucCdb[5] = 0x00; unsigned long ulPrevTime = GetTickCount(); while (true) { // See if one second have passed. if (GetTickCount() > (ulPrevTime + 1000)) { if (pProgress->cancelled()) { // It's safe to abort the format process at this stage. We just need to // close the current track. g_Core2.CloseTrackSession(Device,0,0,true); return false; } unsigned char ucResult; if (!Device.transport_with_sense(ucCdb,6,NULL,0, ckmmc::Device::ckTM_READ,ucSense, ucResult)) { return false; } // Check if we're done. if (ucResult == SCSISTAT_GOOD) return true; // See if we're formating a disc (in background mode). if (ucSense[12] == 0x04 && ucSense[13] == 0x04) { // Update the progress. if (pProgress != NULL) { // If the SKSV bit is set to zero we are done. if (ucSense[15] & 0x80) { unsigned short usProgress = ((unsigned short)ucSense[16] << 8) | ucSense[17]; pProgress->set_progress((unsigned char)(usProgress * 100.0f / 0xFFFF)); } else { pProgress->set_progress(100); return true; } } } else { // If we receive any other sense we're done. return true; } ulPrevTime = GetTickCount(); } } return true; } bool CCore2Format::FormatUnit(ckmmc::Device &Device,CAdvancedProgress *pProgress,bool bFull) { g_pLogDlg->print_line(_T("CCore2Format::FormatUnit")); // Initialize buffers. unsigned char ucBuffer[192]; memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); // Perform a device inquiry. memset(ucCdb,0,16); ucCdb[0] = SCSI_INQUIRY; ucCdb[4] = 192; ucCdb[5] = 0; if (!Device.transport(ucCdb,6,ucBuffer,192,ckmmc::Device::ckTM_READ)) return false; // Make sure the device type is a CDROM. if ((ucBuffer[0] & 0x1F) != 0x05) return false; // Get the device configuration, to see what media that's mounted. memset(ucCdb,0,16); ucCdb[0] = SCSI_GET_CONFIGURATION; ucCdb[8] = 0x08; if (!Device.transport(ucCdb,9,ucBuffer,192,ckmmc::Device::ckTM_READ)) return false; unsigned short usProfile = ucBuffer[6] << 8 | ucBuffer[7]; g_pLogDlg->print_line(_T(" Current profile: 0x%.4X."),usProfile); if (usProfile != PROFILE_DVDPLUSRW && usProfile != PROFILE_DVDPLUSRW_DL && usProfile != PROFILE_DVDRAM && usProfile != PROFILE_DVDMINUSRW_RESTOV && usProfile != PROFILE_DVDMINUSRW_SEQ) { g_pLogDlg->print_line(_T(" Error: Unsupported media.")); return false; } // Read the format capacities length. memset(ucCdb,0,16); ucCdb[0] = SCSI_READ_FORMAT_CAPACITIES; ucCdb[8] = 0x04; ucCdb[9] = 0x00; if (!Device.transport(ucCdb,10,ucBuffer,192,ckmmc::Device::ckTM_READ)) return false; unsigned char ucCapListLen = ucBuffer[3]; g_pLogDlg->print_line(_T(" Capacity list length: %d bytes."),ucCapListLen); if (ucCapListLen % 8 != 0 || ucCapListLen == 0) { g_pLogDlg->print_line(_T(" Error: Invalid capacity list length.")); return false; } // Read the actual format capacities data. memset(ucCdb,0,16); ucCdb[0] = SCSI_READ_FORMAT_CAPACITIES; ucCdb[7] = (ucCapListLen + 0x04) >> 8; ucCdb[8] = (ucCapListLen + 0x04) & 0xFF; ucCdb[9] = 0x00; if (!Device.transport(ucCdb,10,ucBuffer,ucCapListLen + 0x04, ckmmc::Device::ckTM_READ)) { return false; } // Locate the appropriate formattable capacity descriptor. unsigned int uiFmtDescOffset = 0; switch (usProfile) { case PROFILE_DVDPLUSRW: case PROFILE_DVDPLUSRW_DL: for (uiFmtDescOffset = 8; uiFmtDescOffset < ucCapListLen; uiFmtDescOffset += 8) { if (ucBuffer[uiFmtDescOffset + 8] >> 2 == 0x26) break; } break; case PROFILE_DVDRAM: for (uiFmtDescOffset = 8; uiFmtDescOffset < ucCapListLen; uiFmtDescOffset += 8) { if (ucBuffer[uiFmtDescOffset + 8] >> 2 == 0x01) break; } break; case PROFILE_DVDMINUSRW_RESTOV: case PROFILE_DVDMINUSRW_SEQ: for (uiFmtDescOffset = 8; uiFmtDescOffset < ucCapListLen; uiFmtDescOffset += 8) { if (ucBuffer[uiFmtDescOffset + 8] >> 2 == (bFull ? 0x10 : 0x15)) break; } break; } if ((ucBuffer[8] & 0x03) == 0x03) // No media present or unknown capacity. { g_pLogDlg->print_line(_T(" Error: Unable to determine media capacity.")); return false; } else { unsigned int uiCapacity = ucBuffer[4] << 24 | ucBuffer[5] << 16 | ucBuffer[6] << 8 | ucBuffer[7]; g_pLogDlg->print_line(_T(" Disc capacity: %.2f GiB (%I64d bytes)."), ((double)uiCapacity * 2048)/1073741824,(__int64)uiCapacity * 2048); if ((ucBuffer[8] & 0x03) == 0x01) // Unformatted or blank media. g_pLogDlg->print_line(_T(" The disc media is unformatted or blank.")); else if ((ucBuffer[8] & 0x03) == 0x02) // Formatted media. g_pLogDlg->print_line(_T(" The disc media is formatted.")); } // Handle any unhandled events. unsigned char ucEvents; if (g_Core2.HandleEvents(Device,pProgress,ucEvents)) { g_pLogDlg->print_line(_T(" Handled events: 0x%.2X"),ucEvents); } else { return false; } // Start the smoke. pProgress->StartSmoke(); // Format the disc. memset(ucCdb,0,16); ucCdb[0] = SCSI_FORMAT_UNIT; ucCdb[1] = 0x11; ucCdb[5] = 0x00; // Format list header. ucBuffer[uiFmtDescOffset + 0] = 0x00; ucBuffer[uiFmtDescOffset + 1] = 0x02; // Immed. ucBuffer[uiFmtDescOffset + 2] = 0x00; ucBuffer[uiFmtDescOffset + 3] = 0x08; pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINFORMAT), lngGetString(WRITEMODE_REAL)); pProgress->set_status(lngGetString(STATUS_FORMAT)); if (!Device.transport(ucCdb,6,ucBuffer + uiFmtDescOffset,12, ckmmc::Device::ckTM_WRITE)) { pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_FORMAT)); return false; } if (!g_Core2.WaitForUnit(Device,pProgress)) return false; // Stop the background format process (DVD+RW only). if (usProfile == PROFILE_DVDPLUSRW || usProfile == PROFILE_DVDPLUSRW_DL) { // Let the background format continue on DVD+RW discs if a full format was requested. if (bFull) { pProgress->AllowCancel(true); pProgress->set_status(lngGetString(STATUS_FORMATBKGND)); if (!WaitBkgndFormat(Device,pProgress)) return false; } // Stop the background format. pProgress->set_status(lngGetString(STATUS_CLOSETRACK)); if (!g_Core2.CloseTrackSession(Device,0x00,0x00,true)) pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_STOPBKGNDFORMAT)); if (!g_Core2.WaitForUnit(Device,pProgress)) return false; } pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(SUCCESS_FORMAT)); return true; } ================================================ FILE: src/app/core/core2_format.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "advanced_progress.hh" class CCore2Format { private: bool WaitBkgndFormat(ckmmc::Device &Device,CAdvancedProgress *pProgress); public: CCore2Format(); ~CCore2Format(); bool FormatUnit(ckmmc::Device &Device,CAdvancedProgress *pProgress,bool bFull); }; ================================================ FILE: src/app/core/core2_info.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "scsi.hh" #include "log_dlg.hh" #include "core2_info.hh" CCore2Info::CCore2Info() { } CCore2Info::~CCore2Info() { } bool CCore2Info::ReadCapacity(ckmmc::Device &Device,unsigned long &ulBlockAddress, unsigned long &ulBlockLength) { // Initialize buffers. unsigned char ucBuffer[8]; memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[0] = SCSI_READ_CAPACITY; ucCdb[9] = 0; if (!Device.transport(ucCdb,10,ucBuffer,8,ckmmc::Device::ckTM_READ)) return false; ulBlockAddress = ((unsigned long)ucBuffer[0] << 24) | ((unsigned long)ucBuffer[1] << 16) | ((unsigned long)ucBuffer[2] << 8) | ucBuffer[3]; ulBlockLength = ((unsigned long)ucBuffer[4] << 24) | ((unsigned long)ucBuffer[5] << 16) | ((unsigned long)ucBuffer[6] << 8) | ucBuffer[7]; return true; } bool CCore2Info::ReadTrackInformation(ckmmc::Device &Device,eTrackInfoType InfoType, unsigned long ulTrackAddr,CCore2TrackInfo *pTrackInfo) { if (pTrackInfo == NULL) return false; // Initialize buffers. unsigned char ucBuffer[48]; memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[0] = SCSI_READ_TRACK_INFORMATION; ucCdb[1] = static_cast(InfoType & 0x3); ucCdb[2] = 0; ucCdb[2] = (unsigned char)(ulTrackAddr >> 24); ucCdb[3] = (unsigned char)(ulTrackAddr >> 16); ucCdb[4] = (unsigned char)(ulTrackAddr >> 8); ucCdb[5] = (unsigned char)(ulTrackAddr & 0xFF); ucCdb[7] = sizeof(ucBuffer) >> 8; // Allocation length (MSB). ucCdb[8] = sizeof(ucBuffer) & 0xFF; // Allocation length (LSB). ucCdb[9] = 0; if (!Device.transport(ucCdb,10,ucBuffer,sizeof(ucBuffer), ckmmc::Device::ckTM_READ)) { return false; } // Check if we received to much data. unsigned short usDataLength = ((unsigned short)ucBuffer[0] << 8) | ucBuffer[1]; if (usDataLength > (sizeof(ucBuffer) - 2)) g_pLogDlg->print_line(_T(" Warning: CCore2::ReadTrackInformation received more track information than it could handle.")); pTrackInfo->m_ucFlags = (ucBuffer[6] & 0xF0) | ((ucBuffer[5] >> 2) & 0x0C) | (ucBuffer[7] & 0x03); pTrackInfo->m_ucLJRS = (ucBuffer[5] >> 6) & 0x03; pTrackInfo->m_ucTrackMode = ucBuffer[5] & 0x0F; pTrackInfo->m_ucDataMode = ucBuffer[6] & 0x0F; pTrackInfo->m_usTrackNumber = ((unsigned short)ucBuffer[32] << 8) | ucBuffer[2]; pTrackInfo->m_usSessionNumber = ((unsigned short)ucBuffer[33] << 8) | ucBuffer[3]; pTrackInfo->m_ulTrackAddr = ((unsigned int)ucBuffer[8] << 24) | ((unsigned int)ucBuffer[9] << 16) | ((unsigned int)ucBuffer[10] << 8) | ucBuffer[11]; pTrackInfo->m_ulNextWritableAddr = ((unsigned int)ucBuffer[12] << 24) | ((unsigned int)ucBuffer[13] << 16) | ((unsigned int)ucBuffer[14] << 8) | ucBuffer[15]; pTrackInfo->m_ulFreeBlocks = ((unsigned int)ucBuffer[16] << 24) | ((unsigned int)ucBuffer[17] << 16) | ((unsigned int)ucBuffer[18] << 8) | ucBuffer[19]; pTrackInfo->m_ulBlockingFactor = ((unsigned int)ucBuffer[20] << 24) | ((unsigned int)ucBuffer[21] << 16) | ((unsigned int)ucBuffer[22] << 8) | ucBuffer[23]; pTrackInfo->m_ulTrackSize = ((unsigned int)ucBuffer[24] << 24) | ((unsigned int)ucBuffer[25] << 16) | ((unsigned int)ucBuffer[26] << 8) | ucBuffer[27]; pTrackInfo->m_ulLastRecorderAddr = ((unsigned int)ucBuffer[28] << 24) | ((unsigned int)ucBuffer[29] << 16) | ((unsigned int)ucBuffer[30] << 8) | ucBuffer[31]; pTrackInfo->m_ulReadCombLBA = ((unsigned int)ucBuffer[36] << 24) | ((unsigned int)ucBuffer[37] << 16) | ((unsigned int)ucBuffer[38] << 8) | ucBuffer[39]; pTrackInfo->m_ulNextJLA = ((unsigned int)ucBuffer[40] << 24) | ((unsigned int)ucBuffer[41] << 16) | ((unsigned int)ucBuffer[42] << 8) | ucBuffer[43]; pTrackInfo->m_ulLastJLA = ((unsigned int)ucBuffer[44] << 24) | ((unsigned int)ucBuffer[45] << 16) | ((unsigned int)ucBuffer[46] << 8) | ucBuffer[47]; return true; } bool CCore2Info::ReadDiscInformation(ckmmc::Device &Device,CCore2DiscInfo *pDiscInfo) { if (pDiscInfo == NULL) return false; // Initialize buffers. unsigned char ucBuffer[2048]; memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[0] = SCSI_READ_DISC_INFORMATION; ucCdb[1] = 0x00; // Standard disc information. ucCdb[7] = 0x08; ucCdb[8] = 0x00; ucCdb[9] = 0x00; if (!Device.transport(ucCdb,10,ucBuffer,2048,ckmmc::Device::ckTM_READ)) return false; pDiscInfo->m_ucLastSessStatus = (ucBuffer[2] >> 2) & 0x03; pDiscInfo->m_ucDiscStatus = ucBuffer[2] & 0x03; pDiscInfo->m_ucFirstTrack = ucBuffer[3]; pDiscInfo->m_usNumSessions = ucBuffer[4] | (ucBuffer[9] << 8); pDiscInfo->m_usLastSessFstTrack = ucBuffer[5] | (ucBuffer[10] << 8); pDiscInfo->m_usLastSessLstTrack = ucBuffer[6] | (ucBuffer[11] << 8); pDiscInfo->m_ucFlags = (ucBuffer[7] & 0xFC) | (((ucBuffer[2] & 0x10) > 0) << 1); pDiscInfo->m_ucDiscType = ucBuffer[8]; pDiscInfo->m_uiDiscID = (ucBuffer[12] << 24) | (ucBuffer[13] << 16) | (ucBuffer[14] << 8) | ucBuffer[15]; pDiscInfo->m_uiLastSessLeadInAddr = (ucBuffer[16] << 24) | (ucBuffer[17] << 16) | (ucBuffer[18] << 8) | ucBuffer[19]; pDiscInfo->m_uiLastLeadOutAddr = (ucBuffer[20] << 24) | (ucBuffer[21] << 16) | (ucBuffer[22] << 8) | ucBuffer[23]; pDiscInfo->m_uiDiscBarCode = ((unsigned __int64)ucBuffer[24] << 56) | ((unsigned __int64)ucBuffer[25] << 48) | ((unsigned __int64)ucBuffer[26] << 40) | ((unsigned __int64)ucBuffer[27] << 32) | (ucBuffer[28] << 24) | (ucBuffer[29] << 16) | (ucBuffer[30] << 8) | ucBuffer[31]; pDiscInfo->m_ucDiscAppCode = ucBuffer[32]; return true; } bool CCore2Info::ReadPhysFmtInfo(ckmmc::Device &Device,CCore2PhysFmtInfo *pPhysInfo) { if (pPhysInfo == NULL) return false; // Initialize buffers. unsigned char ucBuffer[192]; memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[ 0] = SCSI_READ_DISC_STRUCTURE; ucCdb[ 7] = 0x00; ucCdb[ 8] = 0x08 >> 8; ucCdb[ 9] = 0x08; ucCdb[11] = 0x00; if (!Device.transport(ucCdb,12,ucBuffer,192,ckmmc::Device::ckTM_READ)) return false; //uiBookType = ucBuffer[4] & 0xFF; pPhysInfo->m_ucDiscCategory = ucBuffer[4] >> 4; pPhysInfo->m_ucPartVersion = ucBuffer[4] & 0xF; pPhysInfo->m_ucDiscSize = ucBuffer[5] >> 4; pPhysInfo->m_ucMaxRate = ucBuffer[5] & 0xF; pPhysInfo->m_ucNumLayers = ((ucBuffer[6] & 0x60) >> 5) + 1; pPhysInfo->m_ucTrackPath = (ucBuffer[6] & 0x10) > 0; pPhysInfo->m_ucLayerType = ucBuffer[6] & 0xF; pPhysInfo->m_ucLinearDensity = ucBuffer[7] >> 4; pPhysInfo->m_ucTrackDensity = ucBuffer[7] & 0xF; pPhysInfo->m_uiDataStartSector = (ucBuffer[9] << 16) | (ucBuffer[10] << 8) | ucBuffer[11]; pPhysInfo->m_uiDataEndSector = (ucBuffer[13] << 16) | (ucBuffer[14] << 8) | ucBuffer[15]; pPhysInfo->m_uiLayer0EndSector = (ucBuffer[17] << 16) | (ucBuffer[18] << 8) | ucBuffer[19]; return true; } bool CCore2Info::ReadTOC(ckmmc::Device &Device,unsigned char &ucFirstTrackNumber, unsigned char &ucLastTrackNumber,std::vector &Tracks) { // Initialize buffers. unsigned char ucBuffer[4 + 2048]; // It feels stupid to allocate this much memory when // only 2 bytes of data is needed. The problem is that // some drives (tested with TSSTCorp CD/DVDW SH-S183A SB00) // returns more data then requested which may cause buffer // overruns. memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[0] = SCSI_READ_TOC_PMA_ATIP; ucCdb[2] = 0x00; // TOC. ucCdb[7] = sizeof(ucBuffer) >> 8; // Allocation length (MSB). ucCdb[8] = sizeof(ucBuffer) & 0xFF; // Allocation length (LSB). ucCdb[9] = 0; if (!Device.transport(ucCdb,10,ucBuffer,sizeof(ucBuffer), ckmmc::Device::ckTM_READ)) { return false; } unsigned short usDataLen = ((unsigned short)ucBuffer[0] << 8) | ucBuffer[1]; if (usDataLen < 2) return false; ucFirstTrackNumber = ucBuffer[2]; ucLastTrackNumber = ucBuffer[3]; // Fill the Tracks vector. for (unsigned char uc = ucFirstTrackNumber; uc <= ucLastTrackNumber; uc++) { unsigned char ucCurTrackNumber = ucBuffer[6 + 8 * (uc - 1)]; unsigned long ulTrackAddr = (ucBuffer[8 + 8 * (uc - 1)] << 24) | (ucBuffer[9 + 8 * (uc - 1)] << 16) | (ucBuffer[10 + 8 * (uc - 1)] << 8) | ucBuffer[11 + 8 * (uc - 1)]; Tracks.push_back(CCore2TOCTrackDesc(ucCurTrackNumber,ulTrackAddr)); } return true; } /* Read session information. */ bool CCore2Info::ReadSI(ckmmc::Device &Device,unsigned char &ucFirstSessNumber, unsigned char &ucLastSessNumber, unsigned long &ulLastSessFirstTrackPos) { // Initialize buffers. unsigned char ucBuffer[4 + 2048]; // It feels stupid to allocate this much memory when // only 2 bytes of data is needed. The problem is that // some drives (tested with TSSTCorp CD/DVDW SH-S183A SB00) // returns more data then requested which may cause buffer // overruns. memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[0] = SCSI_READ_TOC_PMA_ATIP; ucCdb[2] = 0x01; // Session information. ucCdb[7] = sizeof(ucBuffer) >> 8; // Allocation length (MSB). ucCdb[8] = sizeof(ucBuffer) & 0xFF; // Allocation length (LSB). ucCdb[9] = 0; if (!Device.transport(ucCdb,10,ucBuffer,sizeof(ucBuffer), ckmmc::Device::ckTM_READ)) { return false; } unsigned short usDataLen = ((unsigned short)ucBuffer[0] << 8) | ucBuffer[1]; if (usDataLen < 2) return false; ucFirstSessNumber = ucBuffer[2]; ucLastSessNumber = ucBuffer[3]; ulLastSessFirstTrackPos = (ucBuffer[8] << 24) | (ucBuffer[9] << 16) | (ucBuffer[10] << 8) |ucBuffer[11]; return true; } /* CCore2Info::GetTotalDiscCapacity -------------------------------- Counts the number of sectors marked as formatted (used) and unformatted/blank (free) on the disc mounted on the specified device. The function returns true of successfull, false otherwise. */ bool CCore2Info::GetTotalDiscCapacity(ckmmc::Device &Device,unsigned __int64 &uiUsedBytes, unsigned __int64 &uiFreeBytes) { g_pLogDlg->print_line(_T("CCore2Info::GetTotalDiscCapacity")); uiUsedBytes = 0; uiFreeBytes = 0; // Initialize buffers. unsigned char ucBuffer[192]; memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); // Get the device configuration, to see what media that's mounted. memset(ucCdb,0,16); ucCdb[0] = SCSI_GET_CONFIGURATION; ucCdb[8] = 0x08; if (!Device.transport(ucCdb,9,ucBuffer,192,ckmmc::Device::ckTM_READ)) return false; unsigned short usProfile = ucBuffer[6] << 8 | ucBuffer[7]; g_pLogDlg->print_line(_T(" Current profile: 0x%.4X."),usProfile); bool bReadOnly = true; switch (usProfile) { case PROFILE_CDR: case PROFILE_CDRW: case PROFILE_DVDMINUSR_SEQ: case PROFILE_DVDRAM: case PROFILE_DVDMINUSRW_RESTOV: case PROFILE_DVDMINUSRW_SEQ: case PROFILE_DVDMINUSR_DL_SEQ: case PROFILE_DVDMINUSR_DL_JUMP: case PROFILE_DVDPLUSRW: case PROFILE_DVDPLUSR: case PROFILE_DVDPLUSRW_DL: case PROFILE_DVDPLUSR_DL: case PROFILE_BDR_SRM: case PROFILE_BDR_RRM: case PROFILE_BDRE: case PROFILE_HDDVDR: case PROFILE_HDDVDRAM: bReadOnly = false; break; } // Read the format capacities length. memset(ucCdb,0,16); ucCdb[0] = SCSI_READ_FORMAT_CAPACITIES; ucCdb[8] = 0x04; ucCdb[9] = 0x00; if (!Device.transport(ucCdb,10,ucBuffer,192,ckmmc::Device::ckTM_READ)) return false; unsigned char ucCapListLen = ucBuffer[3]; g_pLogDlg->print_line(_T(" Capacity list length: %d bytes."),ucCapListLen); if (ucCapListLen % 8 != 0 || ucCapListLen == 0) { g_pLogDlg->print_line(_T(" Error: Invalid capacity list length.")); return false; } // Read the actual format capacities data. memset(ucCdb,0,16); ucCdb[0] = SCSI_READ_FORMAT_CAPACITIES; ucCdb[7] = (ucCapListLen + 0x04) >> 8; ucCdb[8] = (ucCapListLen + 0x04) & 0xFF; ucCdb[9] = 0x00; if (!Device.transport(ucCdb,10,ucBuffer,ucCapListLen + 0x04, ckmmc::Device::ckTM_READ)) { return false; } if ((ucBuffer[8] & 0x03) == 0x03) // No media present or unknown capacity. { g_pLogDlg->print_line(_T(" No media present.")); return false; } // Format descriptors. for (unsigned int i = 0; i < ucCapListLen; i += 8) { unsigned int uiCapacity = ucBuffer[i + 4] << 24 | ucBuffer[i + 5] << 16 | ucBuffer[i + 6] << 8 | ucBuffer[i + 7]; unsigned int uiBlockSpare = ucBuffer[i + 9] << 16 |ucBuffer[i + 10] << 8 | ucBuffer[i + 11]; if (uiBlockSpare == 2048) { if (ucBuffer[i + 8] == 0x02) // Formatted media uiUsedBytes += (unsigned __int64)uiCapacity * 2048; else if (ucBuffer[i + 8] == 0x01) // Unformatted or blank media. uiFreeBytes += (unsigned __int64)uiCapacity * 2048; } } return true; } bool CCore2Info::GetDiscDVDRegion(ckmmc::Device &Device,unsigned char &ucRegion) { // Initialize buffers. unsigned char ucBuffer[8]; memset(ucBuffer,0,sizeof(ucBuffer)); unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); ucCdb[ 0] = SCSI_READ_DISC_STRUCTURE; ucCdb[ 7] = 0x01; ucCdb[ 8] = 0x08 >> 8; ucCdb[ 9] = 0x08; ucCdb[11] = 0x00; if (!Device.transport(ucCdb,12,ucBuffer,8,ckmmc::Device::ckTM_READ)) return false; unsigned char ucRegMask = ucBuffer[5]; ucRegion = 0; if (ucRegMask != 0xFF) { for (unsigned char i = 0; i < 8; i++) { if (!((ucRegMask >> i) & 0x01)) ucRegion = i + 1; } } return true; } ================================================ FILE: src/app/core/core2_info.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include class CCore2TrackInfo { public: // Flags. enum { FLAG_NWAV = 0x01,FLAG_LRAV = 0x02,FLAG_COPY = 0x04,FLAG_DAMAGE = 0x08, FLAG_FP = 0x10,FLAG_PACKET = 0x20,FLAG_BLANK = 0x40,FLAG_RT = 0x80 }; // Data modes. enum { DM_MODE1 = 0x1,DM_MODE2 = 0x2,DM_UNKNOWN = 0xF }; unsigned char m_ucFlags; unsigned char m_ucLJRS; unsigned char m_ucTrackMode; unsigned char m_ucDataMode; unsigned short m_usTrackNumber; unsigned short m_usSessionNumber; unsigned long m_ulTrackAddr; unsigned long m_ulNextWritableAddr; unsigned long m_ulFreeBlocks; unsigned long m_ulBlockingFactor; unsigned long m_ulTrackSize; unsigned long m_ulLastRecorderAddr; unsigned long m_ulReadCombLBA; unsigned long m_ulNextJLA; unsigned long m_ulLastJLA; }; class CCore2DiscInfo { public: // Last session status. enum { LSS_EMTPY,LSS_INCOMPLETE,LSS_RESERVED,LSS_COMPLETE }; // Disc status. enum { DS_EMTPY,DS_INCOMPLETE,DS_FINALIZED,DS_RANDOMACCESS }; // Disc type. enum { DT_CDDA = 0x00,DT_CDI = 0x10,DT_XA = 0x20,DT_UNDEFINED = 0xFF }; // Flags. enum { FLAG_ERASABLE = 0x02,FLAG_D = 0x04,FLAG_RESERVED = 0x08,FLAG_DACV = 0x10, FLAG_URU = 0x20,FLAG_DBCV = 0x40,FLAG_DIDV = 0x80 }; unsigned char m_ucFlags; unsigned char m_ucLastSessStatus; unsigned char m_ucDiscStatus; unsigned char m_ucDiscType; unsigned char m_ucFirstTrack; unsigned short m_usNumSessions; unsigned short m_usLastSessFstTrack; unsigned short m_usLastSessLstTrack; unsigned int m_uiDiscID; unsigned int m_uiLastSessLeadInAddr; unsigned int m_uiLastLeadOutAddr; unsigned __int64 m_uiDiscBarCode; unsigned char m_ucDiscAppCode; }; class CCore2TOCTrackDesc { public: CCore2TOCTrackDesc(unsigned char ucTrackNumber,unsigned long ulTrackAddr) { m_ucTrackNumber = ucTrackNumber; m_ulTrackAddr = ulTrackAddr; } unsigned char m_ucTrackNumber; unsigned long m_ulTrackAddr; }; class CCore2PhysFmtInfo { public: // Disc category. enum { DC_DVDROM,DC_DVDRAM,DC_DVDR,DC_DVDRW,DC_HDDVDROM,DC_HDDVDRAM,DC_HDDVDR, DC_RESERVED1,DC_RESERVED2,DC_DVDPLUSRW,DC_DVDPLUSR,DC_RESERVED3, DC_RESERVED4,DC_DVDPLUSRWDL,DC_DVDPLUSRDL,DC_RESERVED5 }; // Maximum rate. enum { MR_252 = 0x0,MR_504 = 0x1,MR_1008 = 0x2,MR_2016 = 0x3,MR_3024 = 0x4, MR_NOTSPECIFIED = 0xF }; // Track path. enum { TP_PARALLEL,TP_OPPOSITE }; unsigned char m_ucDiscCategory; unsigned char m_ucPartVersion; unsigned char m_ucDiscSize; unsigned char m_ucMaxRate; unsigned char m_ucNumLayers; unsigned char m_ucLayerType; unsigned char m_ucTrackPath; unsigned char m_ucLinearDensity; unsigned char m_ucTrackDensity; unsigned int m_uiDataStartSector; unsigned int m_uiDataEndSector; unsigned int m_uiLayer0EndSector; }; class CCore2Info { public: enum eTrackInfoType { TIT_LBA = 0, TIT_TRACK = 1, TIT_SESSION = 2 }; CCore2Info(); ~CCore2Info(); // Closely related to SCSI MMC functions. bool ReadCapacity(ckmmc::Device &Device,unsigned long &ulBlockAddress, unsigned long &ulBlockLength); bool ReadTrackInformation(ckmmc::Device &Device,eTrackInfoType InfoType, unsigned long ulTrackAddr,CCore2TrackInfo *pTrackInfo); bool ReadDiscInformation(ckmmc::Device &Device,CCore2DiscInfo *pDiscInfo); bool ReadPhysFmtInfo(ckmmc::Device &Device,CCore2PhysFmtInfo *pPhysInfo); bool ReadTOC(ckmmc::Device &Device,unsigned char &ucFirstTrackNumber, unsigned char &ucLastTrackNumber,std::vector &Tracks); bool ReadSI(ckmmc::Device &Device,unsigned char &ucFirstSessNumber, unsigned char &ucLastSessNumber,unsigned long &ulLastSessFirstTrackPos); bool GetTotalDiscCapacity(ckmmc::Device &Device,unsigned __int64 &uiUsedBytes, unsigned __int64 &uiFreeBytes); bool GetDiscDVDRegion(ckmmc::Device &Device,unsigned char &ucRegion); }; ================================================ FILE: src/app/core/core2_read.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "core2_read.hh" #include "core2.hh" #include "core2_info.hh" #include "core2_util.hh" #include "log_dlg.hh" #include "string_table.hh" #include "lang_util.hh" namespace Core2ReadFunction { CReadFunction::CReadFunction(ckmmc::Device &Device) : m_Device(Device) { } bool CReadFunction::ReadCD(unsigned char *pBuffer,unsigned long ulAddress,unsigned long ulBlockCount, eMainChannelData MCD,eSubChannelData SCD,eC2ErrorInfo ErrorInfo) { if (pBuffer == NULL) return false; // Initialize buffers. unsigned char ucCdb[16]; memset(ucCdb,0,sizeof(ucCdb)); if (ulBlockCount > 0xFFFFFF) g_pLogDlg->print_line(_T(" Warning: Requested block count to large, trunkated the number of block requested to read.")); ucCdb[ 0] = SCSI_READ_CD; ucCdb[ 1] = 0; // Return all types of sectors. ucCdb[ 2] = static_cast(ulAddress >> 24); ucCdb[ 3] = static_cast(ulAddress >> 16); ucCdb[ 4] = static_cast(ulAddress >> 8); ucCdb[ 5] = static_cast(ulAddress & 0xFF); ucCdb[ 6] = static_cast(ulBlockCount >> 16); ucCdb[ 7] = static_cast(ulBlockCount >> 8); ucCdb[ 8] = static_cast(ulBlockCount & 0xFF); ucCdb[ 9] = static_cast(0 | MCD | ErrorInfo); ucCdb[11] = 0; switch (SCD) { case SCD_FORMATTEDQ: ucCdb[10] = 0x02; break; case SCD_DEINTERLEAVED_RW: ucCdb[10] = 0x04; break; } if (!m_Device.transport(ucCdb,12,pBuffer,ulBlockCount * GetFrameSize(), ckmmc::Device::ckTM_READ)) { return false; } return true; } CReadUserData::CReadUserData(ckmmc::Device &Device,ckcore::OutStream *pOutStream) : CReadFunction(Device),m_pOutStream(pOutStream) { // Get the block size in bytes (the frame only contains the user data in this case). CCore2Info Core2Info; unsigned long ulBlockAddress = 0; if (!Core2Info.ReadCapacity(Device,ulBlockAddress,m_ulFrameSize)) { m_ulFrameSize = 2048; g_pLogDlg->print_line(_T(" Error: Unable to obtain disc block information, impossible to continue.")); } g_pLogDlg->print_line(_T(" Block address: %u, block length: %u."),ulBlockAddress,m_ulFrameSize); } CReadUserData::~CReadUserData() { } bool CReadUserData::Read(unsigned char *pBuffer,unsigned long ulAddress, unsigned long ulBlockCount) { return ReadCD(pBuffer,ulAddress,ulBlockCount,MCD_USERDATA,SCD_NONE,C2EI_NONE); } bool CReadUserData::Process(unsigned char *pBuffer,unsigned long ulBlockCount) { return m_pOutStream->write(pBuffer,ulBlockCount * m_ulFrameSize) != 1; } unsigned long CReadUserData::GetFrameSize() { return m_ulFrameSize; } CReadC2::CReadC2(ckmmc::Device &Device) : CReadFunction(Device) { m_ulErrSecCount = 0; m_ulErrByteCount = 0; m_uiTotalBytes = 0; } CReadC2::~CReadC2() { } /* CReadC2::NumBits ---------------- Returns the number of bits in the specified byte. */ unsigned char CReadC2::NumBits(unsigned char ucData) { unsigned char ucResult = 0; if (ucData & 0x01) ucResult++; if (ucData & 0x02) ucResult++; if (ucData & 0x04) ucResult++; if (ucData & 0x08) ucResult++; if (ucData & 0x10) ucResult++; if (ucData & 0x20) ucResult++; if (ucData & 0x40) ucResult++; if (ucData & 0x80) ucResult++; return ucResult; } bool CReadC2::Read(unsigned char *pBuffer,unsigned long ulAddress, unsigned long ulBlockCount) { return ReadCD(pBuffer,ulAddress,ulBlockCount,MCD_NONE,SCD_NONE,C2EI_BITS); } bool CReadC2::Process(unsigned char *pBuffer,unsigned long ulBlockCount) { bool bSecErr = false; const unsigned char *pBlockBuffer = pBuffer; for (unsigned long i = 0; i < ulBlockCount; i++) { for (unsigned int j = 0; j < 294; j++) { // A little optimization. if (pBlockBuffer[j] == 0) continue; m_ulErrByteCount += NumBits(pBlockBuffer[j]); bSecErr = true; } // Increase the error sector counter. if (bSecErr) { m_ulErrSecCount++; bSecErr = false; } pBlockBuffer += 294; } m_uiTotalBytes += (ulBlockCount * 294) << 3; return true; } unsigned long CReadC2::GetFrameSize() { return 294; } } CCore2Read::CCore2Read() { } CCore2Read::~CCore2Read() { } /* CCore2Read::RetryReadBlock -------------------------- Tries various methods to successfully re-read the sector at the specified address. */ bool CCore2Read::RetryReadBlock(ckmmc::Device &Device,CAdvancedProgress *pProgress, Core2ReadFunction::CReadFunction *pReadFunction, unsigned char *pBuffer,unsigned long ulAddress) { unsigned char ucDummyBuffer[CORE2_READ_MAXFRAMESIZE]; // Try to re-read each sector CORE2_READ_RETRYCOUNT number of times. for (unsigned int i = 0; i < CORE2_READ_RETRYCOUNT; i++) { if (pProgress != NULL) { pProgress->set_status(lngGetString(STATUS_REREADSECTOR),ulAddress, i + 1,CORE2_READ_RETRYCOUNT); // Check if the operation has been cancelled. if (pProgress->cancelled()) return false; } g_Core2.WaitForUnit(Device,pProgress); // Read the first 10 sectors without seeking. if (i > 10) { if ((i % 4) == 0) { // Read the first sector. pReadFunction->Read(ucDummyBuffer,0,1); } else { // Reed a random sector before the requested sector. pReadFunction->Read(ucDummyBuffer,rand() % ulAddress,1); } g_Core2.WaitForUnit(Device,pProgress); } // Re-read the requested sector. if (pReadFunction->Read(pBuffer,ulAddress,1)) return true; } return false; } bool CCore2Read::ReadData(ckmmc::Device &Device,CAdvancedProgress *pProgress, Core2ReadFunction::CReadFunction *pReadFunction,unsigned long ulStartBlock, unsigned long ulNumBlocks,bool bIgnoreErr) { //g_pLogDlg->print_line(_T("CCore2Read::ReadData")); // Make sure that the device supports this operation. if (!Device.support(ckmmc::Device::ckDEVICE_MULTIREAD)) { g_pLogDlg->print_line(_T(" Error: The selected device does not support this kind of operation.")); return false; } if (!Device.support(ckmmc::Device::ckDEVICE_CD_READ)) { if (pProgress != NULL) pProgress->notify(ckcore::Progress::ckERROR,lngGetString(FAILURE_NOMEDIA)); g_pLogDlg->print_line(_T(" Error: The selected device does not support this kind of operation.")); return false; } // Make sure that a disc is inserted. ckmmc::Device::Profile Profile = Device.profile(); if (Profile == ckmmc::Device::ckPROFILE_NONE) { g_pLogDlg->print_line(_T(" Error: No disc inserted.")); return false; } // Status related (ulWritten counts the number of blocks/sectors written). unsigned long ulWritten = 0; unsigned long ulLastTime = GetTickCount(); // Read the data. unsigned char *pReadBuffer = new unsigned char[pReadFunction->GetFrameSize() * /*CORE2_READ_MAXFRAMESIZE * */CORE2_READ_BLOCKCOUNT]; unsigned long ulReadCount = CORE2_READ_BLOCKCOUNT; unsigned long ulEndBlock = ulStartBlock + ulNumBlocks; for (unsigned long l = ulStartBlock; l < ulEndBlock; l += ulReadCount) { if ((l + ulReadCount) > ulEndBlock) ulReadCount = ulEndBlock - l; // Update the status every second. if (GetTickCount() > ulLastTime + 1000) { if (pProgress != NULL) { pProgress->set_status(lngGetString(STATUS_READTRACK2), ckmmc::util::kb_to_human_speed(ulWritten * 2352 / 1000,Profile)); } ulWritten = 0; ulLastTime = GetTickCount(); } // Check if the operation has been cancelled. if (pProgress != NULL && pProgress->cancelled()) { delete [] pReadBuffer; return false; } if (!pReadFunction->Read(pReadBuffer,l,ulReadCount)) { g_pLogDlg->print_line(_T(" Warning: Failed to read sector range %u-%u"), l,l + ulReadCount); if (pProgress != NULL) pProgress->notify(ckcore::Progress::ckWARNING,lngGetString(FAILURE_READSOURCEDISC),l); // Read the sectors in the failed sector range one by one. for (unsigned int j = 0; j < ulReadCount; j++) { // Check if the operation has been cancelled. if (pProgress != NULL && pProgress->cancelled()) { delete [] pReadBuffer; return false; } if (!RetryReadBlock(Device,pProgress,pReadFunction,pReadBuffer + j * pReadFunction->GetFrameSize(),l + j)) { g_pLogDlg->print_line(_T(" Retry on sector %u failed."),l+j); // Check if we're allowed to ignore this error. if (!bIgnoreErr) { if (pProgress != NULL) pProgress->notify(ckcore::Progress::ckERROR,lngGetString(ERROR_SECTOR),l + j); delete [] pReadBuffer; return false; } if (pProgress != NULL) pProgress->notify(ckcore::Progress::ckWARNING,lngGetString(ERROR_SECTOR),l + j); } } } if (!pReadFunction->Process(pReadBuffer,ulReadCount)) { g_pLogDlg->print_line(_T(" Error: Unable to process read data.")); delete [] pReadBuffer; return false; } if (pProgress != NULL) pProgress->set_progress((unsigned char)(((double)l/ulEndBlock) * 100)); ulWritten += ulReadCount; } delete [] pReadBuffer; return true; } ================================================ FILE: src/app/core/core2_read.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include "advanced_progress.hh" #define CORE2_READ_RETRYCOUNT 1 #define CORE2_READ_MAXFRAMESIZE (2352 + 96 + 296) // Mainchannel + RAW P-W subchannel + C2 block information. #define CORE2_READ_BLOCKCOUNT 20 // Read 20 blocks at a time. namespace Core2ReadFunction { class CReadFunction { private: ckmmc::Device &m_Device; protected: enum eMainChannelData { MCD_NONE = 0x00, MCD_USERDATA = 0x10 }; enum eSubChannelData { SCD_NONE, SCD_FORMATTEDQ, SCD_DEINTERLEAVED_RW }; enum eC2ErrorInfo { C2EI_NONE = 0x0, C2EI_BITS = 0x2, // 294 bytes. C2EI_BLOCKANDBITS = 0x4, // 296 bytes. }; bool ReadCD(unsigned char *pBuffer,unsigned long ulAddress,unsigned long ulBlockCount, eMainChannelData MCD,eSubChannelData SCD,eC2ErrorInfo ErrorInfo); public: CReadFunction(ckmmc::Device &Device); virtual bool Read(unsigned char *pBuffer,unsigned long ulAddress, unsigned long ulBlockCount) = 0; virtual bool Process(unsigned char *pBuffer,unsigned long ulBlockCount) = 0; virtual unsigned long GetFrameSize() = 0; }; class CReadUserData : public CReadFunction { private: ckcore::OutStream *m_pOutStream; unsigned long m_ulFrameSize; public: CReadUserData(ckmmc::Device &Device,ckcore::OutStream *pOutStream); ~CReadUserData(); bool Read(unsigned char *pBuffer,unsigned long ulAddress, unsigned long ulBlockCount); bool Process(unsigned char *pBuffer,unsigned long ulBlockCount); unsigned long GetFrameSize(); }; class CReadRaw { }; class CReadC2 : public CReadFunction { private: unsigned long m_ulErrSecCount; unsigned long m_ulErrByteCount; unsigned __int64 m_uiTotalBytes; unsigned char NumBits(unsigned char ucData); public: CReadC2(ckmmc::Device &Device); ~CReadC2(); bool Read(unsigned char *pBuffer,unsigned long ulAddress, unsigned long ulBlockCount); bool Process(unsigned char *pBuffer,unsigned long ulBlockCount); unsigned long GetFrameSize(); }; } class CCore2Read { private: enum eSubChannelData { SUBCHANNELDATA_NONE, SUBCHANNELDATA_FORMATTEDQ, SUBCHANNELDATA_DEINTERLEAVED_RW }; bool RetryReadBlock(ckmmc::Device &Device,CAdvancedProgress *pProgress, Core2ReadFunction::CReadFunction *pReadFunction,unsigned char *pBuffer, unsigned long ulAddress); public: CCore2Read(); ~CCore2Read(); bool ReadData(ckmmc::Device &Device,CAdvancedProgress *pProgress, Core2ReadFunction::CReadFunction *pReadFunction,unsigned long ulStartBlock, unsigned long ulNumBlocks,bool bIgnoreErr); }; ================================================ FILE: src/app/core/core2_stream.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "core2_read.hh" #include "core2_stream.hh" CCore2InStream::CCore2InStream(ckcore::Log *pLog,ckmmc::Device &Device, unsigned long ulStartBlock,unsigned long ulEndBlock) : m_pLog(pLog),m_Device(Device),m_ReadFunc(Device,&m_Stream),m_ulStartBlock(ulStartBlock), m_ulEndBlock(ulEndBlock),m_ulCurBlock(ulStartBlock) { m_ulBufferData = 0; m_ulBufferPos = 0; m_ulBufferSize = m_ReadFunc.GetFrameSize() * CORE2_INSTREAM_FRAMEFACTOR; m_pBuffer = new unsigned char[m_ulBufferSize]; m_Stream.SetBuffer(m_pBuffer,m_ulBufferSize); } CCore2InStream::~CCore2InStream() { if (m_pBuffer != NULL) { delete [] m_pBuffer; m_pBuffer = NULL; m_ulBufferSize = 0; } } unsigned long CCore2InStream::GetSafeFrameReadCount() { if (m_ulEndBlock - m_ulCurBlock < CORE2_INSTREAM_FRAMEFACTOR) return m_ulEndBlock - m_ulCurBlock; else return CORE2_INSTREAM_FRAMEFACTOR; } /* Not to be confused with other BytesToSector functions that calculates The number of sectors to store the specified number of bytes. This function calculates in which frame the last byte is stored. */ unsigned long CCore2InStream::BytesToFrame(unsigned __int64 uiBytes) { if (uiBytes == 0) return 0; unsigned long ulSectors = 0; while (uiBytes > m_ReadFunc.GetFrameSize()) { uiBytes -= m_ReadFunc.GetFrameSize(); ulSectors++; } return ulSectors; } bool CCore2InStream::FillBuffer() { unsigned long ulNumFrames = GetSafeFrameReadCount(); if (!m_Read.ReadData(m_Device,NULL,&m_ReadFunc,m_ulCurBlock,ulNumFrames,false)) { m_pLog->print_line(_T(" Error: Unable to read user data from disc (%u, %u)."), m_ulCurBlock,ulNumFrames); return false; } m_ulBufferData = m_Stream.GetBufferDataSize(); m_ulBufferPos = 0; m_ulCurBlock += ulNumFrames; return true; } ckcore::tint64 CCore2InStream::read(void *pBuffer,ckcore::tuint32 uiCount) { if (end()) return -1; // W00t? This was discovered when switching to ckcore. ckcore::tint64 iResult = 0; // Check if the requested data can be found in the buffer. if (uiCount <= m_ulBufferData - m_ulBufferPos) { memcpy(pBuffer,m_pBuffer + m_ulBufferPos,uiCount); m_ulBufferPos += uiCount; iResult = uiCount; } else { // First copy everything we have in the buffer. unsigned long ulInBuffer = m_ulBufferData - m_ulBufferPos; memcpy(pBuffer,m_pBuffer + m_ulBufferPos,ulInBuffer); m_ulBufferPos += ulInBuffer; unsigned long ulRemain = uiCount - ulInBuffer; if (end()) return ulInBuffer; // Check if we can read more from the CD. if (!FillBuffer()) return -1; if (ulRemain > m_ulBufferData - m_ulBufferPos) { // FIXME: Is execution of this block possible? unsigned long ulCanRead = m_ulBufferData - m_ulBufferPos; memcpy((unsigned char *)pBuffer + ulInBuffer,m_pBuffer + m_ulBufferPos,ulCanRead); m_ulBufferPos += ulCanRead; iResult = ulInBuffer + ulCanRead; } else { memcpy((unsigned char *)pBuffer + ulInBuffer,m_pBuffer + m_ulBufferPos,ulRemain); m_ulBufferPos += ulRemain; iResult = uiCount; } } return iResult; } ckcore::tint64 CCore2InStream::size() { return -1; } bool CCore2InStream::end() { return m_ulCurBlock >= m_ulEndBlock && m_ulBufferPos >= m_ulBufferData; } bool CCore2InStream::seek(ckcore::tuint32 uiDistance,ckcore::InStream::StreamWhence Whence) { if (Whence == ckcore::InStream::ckSTREAM_BEGIN) { unsigned long ulFrame = BytesToFrame(uiDistance); // Calculate which sector the byte distance corresponds to. m_ulCurBlock = m_ulStartBlock + ulFrame; if (!FillBuffer()) return false; m_ulBufferPos = (unsigned long)(uiDistance - ulFrame * m_ReadFunc.GetFrameSize()); return true; } else { // Check if we can just move forward in the internal buffer. if (uiDistance < m_ulBufferData - m_ulBufferPos) { m_ulBufferPos += (unsigned long)uiDistance; } else { // In which internal frame are we? unsigned long ulFrame = BytesToFrame(m_ulBufferPos); // Search through the current frame. ulFrame++; __int64 iRemain = uiDistance - (m_ulBufferData - m_ulBufferPos); // How many more frames should we move through. ulFrame += BytesToFrame(iRemain); m_ulCurBlock = m_ulStartBlock + ulFrame; if (!FillBuffer()) return false; m_ulBufferPos = (unsigned long)(iRemain - ulFrame * m_ReadFunc.GetFrameSize()); return true; } } return true; } ================================================ FILE: src/app/core/core2_stream.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include "core2_read.hh" #define CORE2_INSTREAM_FRAMEFACTOR 10 // We will cache 10 frames in the memory. class CCore2InStream : public ckcore::InStream { private: class CInternalStream : public ckcore::OutStream { private: unsigned char *m_pBuffer; unsigned long m_ulBufferSize; unsigned long m_ulBufferData; public: CInternalStream() : m_pBuffer(NULL),m_ulBufferSize(0),m_ulBufferData(0) { } void SetBuffer(unsigned char *pBuffer,unsigned long ulBufferSize) { m_pBuffer = pBuffer; m_ulBufferSize = ulBufferSize; } ckcore::tint64 write(const void *pBuffer,ckcore::tuint32 uiCount) { if (m_pBuffer == NULL) return -1; if (m_ulBufferSize < uiCount) return -1; memcpy(m_pBuffer,pBuffer,uiCount); m_ulBufferData = uiCount; return uiCount; } unsigned long GetBufferDataSize() { return m_ulBufferData; } }; CInternalStream m_Stream; unsigned char *m_pBuffer; unsigned long m_ulBufferSize; unsigned long m_ulBufferData; // The amount of data that's stored in the buffer. unsigned long m_ulBufferPos; const unsigned long m_ulStartBlock; // The start sector to use as beginning of the stream. const unsigned long m_ulEndBlock; // The last sector. unsigned long m_ulCurBlock; ckcore::Log *m_pLog; ckmmc::Device &m_Device; Core2ReadFunction::CReadUserData m_ReadFunc; CCore2Read m_Read; unsigned long GetSafeFrameReadCount(); unsigned long BytesToFrame(unsigned __int64 uiBytes); bool FillBuffer(); public: CCore2InStream(ckcore::Log *pLog,ckmmc::Device &Device, unsigned long ulStartBlock,unsigned long ulEndBlock); ~CCore2InStream(); // ckCore::InStream. ckcore::tint64 read(void *pBuffer,ckcore::tuint32 uiCount); ckcore::tint64 size(); bool end(); bool seek(ckcore::tuint32 uiDistnace,ckcore::InStream::StreamWhence Whence); }; ================================================ FILE: src/app/core/core2_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "scsi.hh" #include "core2_util.hh" /** Parses the specified sense buffer and returns a value representing the specific error. @param pSenseBuf a pointer to the sense buffer, it should be atleast 24 bytes long @return the correcsponding internal error value. */ unsigned char CheckSense(unsigned char *pSenseBuf) { // Sense key. switch (pSenseBuf[2] & 0x0F) { case 0x02: { // Additional sense code. switch (pSenseBuf[12]) { case 0x04: { // Additional sense code qualifier. switch (pSenseBuf[13]) { case 0x04: return SENSE_FORMATINPROGRESS; case 0x08: return SENSE_LONGWRITEINPROGRESS; } } break; } } break; case 0x05: { // Additional sense code. switch (pSenseBuf[12]) { case 0x64: { switch (pSenseBuf[13]) { case 0x00: return SENSE_ILLEGALMODEFORTHISTRACK; case 0x01: return SENSE_INVALIDPACKETSIZE; } } break; } } break; } return 0; } ================================================ FILE: src/app/core/core2_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #define SENSE_FORMATINPROGRESS 0x01 #define SENSE_LONGWRITEINPROGRESS 0x02 #define SENSE_ILLEGALMODEFORTHISTRACK 0x03 #define SENSE_INVALIDPACKETSIZE 0x04 unsigned char CheckSense(unsigned char *pSenseBuf); ================================================ FILE: src/app/core/diagnostics.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "cdrtools_parse_strings.hh" #include "log_dlg.hh" #include "settings.hh" #include "core.hh" #include "diagnostics.hh" CDiagnostics g_Diagnostics; CDiagnostics::CDiagnostics() { } CDiagnostics::~CDiagnostics() { } void CDiagnostics::event_output(const std::string &block) { // Always skip the copyright line. if (!strncmp(block.c_str(),CDRTOOLS_COPYRIGHT,CDRTOOLS_COPYRIGHT_LENGTH)) return; g_pLogDlg->print(_T(" > ")); g_pLogDlg->print_line(ckcore::string::ansi_to_auto<1024>(block.c_str()).c_str()); } void CDiagnostics::event_finished() { g_pLogDlg->print_line(_T("CDiagnostics::ProcessEnded")); g_pLogDlg->print_line(_T("")); } bool CDiagnostics::DeviceScan() { g_pLogDlg->print_line(_T("CDiagnostics::DeviceScan")); TCHAR szCommandLine[MAX_PATH]; lstrcpy(szCommandLine,_T("\"")); lstrcat(szCommandLine,g_GlobalSettings.m_szCDRToolsPath); lstrcat(szCommandLine,_T(CORE_WRITEAPP)); #ifdef CDRKIT lstrcat(szCommandLine,_T("\" -devices")); #else lstrcat(szCommandLine,_T("\" -scanbus")); #endif if (!create(szCommandLine)) return false; return true; } ================================================ FILE: src/app/core/diagnostics.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include class CDiagnostics : public ckcore::Process { private: // Events. void event_output(const std::string &block); void event_finished(); public: CDiagnostics(); ~CDiagnostics(); bool DeviceScan(); }; extern CDiagnostics g_Diagnostics; ================================================ FILE: src/app/core/scsi.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "scsi.hh" ================================================ FILE: src/app/core/scsi.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once // SCSI statuses. #define SCSISTAT_GOOD 0x00 #define SCSISTAT_CHECK_CONDITION 0x02 #define SCSISTAT_CONDITION_MET 0x04 #define SCSISTAT_BUSY 0x08 #define SCSISTAT_INTERMEDIATE 0x10 #define SCSISTAT_INTERMEDIATE_COND_MET 0x14 #define SCSISTAT_RESERVATION_CONFLICT 0x18 #define SCSISTAT_COMMAND_TERMINATED 0x22 #define SCSISTAT_QUEUE_FULL 0x28 // SCSI commands. #define SCSI_INQUIRY 0x12 #define SCSI_READ_CAPACITY 0x25 #define SCSI_READ_TOC_PMA_ATIP 0x43 #define SCSI_GET_CONFIGURATION 0x46 #define SCSI_READ_DISC_INFORMATION 0x51 #define SCSI_READ_DISC_STRUCTURE 0xAD #define SCSI_READ_FORMAT_CAPACITIES 0x23 #define SCSI_FORMAT_UNIT 0x04 #define SCSI_GET_EVENT_STATUS_NOTIFICATION 0x4A #define SCSI_TEST_UNIT_READY 0x00 #define SCSI_START_STOP_UNIT 0x1B #define SCSI_CLOSE_TRACK_SESSION 0x5B #define SCSI_PREVENTALLOW_MEDIUM_REMOVAL 0x1E #define SCSI_GET_PERFORMANCE 0xAC #define SCSI_SET_CD_SPEED 0xBB #define SCSI_BLANK 0xA1 #define SCSI_MODE_SENSE10 0x5A #define SCSI_MODE_SELECT10 0x55 #define SCSI_REQUEST_SENSE 0x03 #define SCSI_READ_CD 0xBE #define SCSI_READ_TRACK_INFORMATION 0x52 // Profiles. #define PROFILE_NONE 0x0000 #define PROFILE_NONREMOVABLE 0x0001 #define PROFILE_REMOVABLE 0x0002 #define PROFILE_MOPTIC_E 0x0003 #define PROFILE_OPTIC_WO 0x0004 #define PROFILE_AS_MO 0x0005 #define PROFILE_CDROM 0x0008 #define PROFILE_CDR 0x0009 #define PROFILE_CDRW 0x000A #define PROFILE_DVDROM 0x0010 #define PROFILE_DVDMINUSR_SEQ 0x0011 #define PROFILE_DVDRAM 0x0012 #define PROFILE_DVDMINUSRW_RESTOV 0x0013 #define PROFILE_DVDMINUSRW_SEQ 0x0014 #define PROFILE_DVDMINUSR_DL_SEQ 0x0015 #define PROFILE_DVDMINUSR_DL_JUMP 0x0016 #define PROFILE_DVDPLUSRW 0x001A #define PROFILE_DVDPLUSR 0x001B //#define PROFILE_DDCDROM 0x0020 //#define PROFILE_DDCDR 0x0021 //#define PROFILE_DDCDRW 0x0022 #define PROFILE_DVDPLUSRW_DL 0x002A #define PROFILE_DVDPLUSR_DL 0x002B #define PROFILE_BDROM 0x0040 #define PROFILE_BDR_SRM 0x0041 #define PROFILE_BDR_RRM 0x0042 #define PROFILE_BDRE 0x0043 #define PROFILE_HDDVDROM 0x0050 #define PROFILE_HDDVDR 0x0051 #define PROFILE_HDDVDRAM 0x0052 #define PROFILE_NONSTANDARD 0xFFFF // Sense keys. #define SENSEKEY_NO_SENSE 0x00 #define SENSEKEY_RECOVERED_ERROR 0x01 #define SENSEKEY_NOT_READY 0x02 #define SENSEKEY_MEDIUM_ERROR 0x03 // Non recoverable error. #define SENSEKEY_HARDWARE_ERROR 0x04 // Non recoverable error. #define SENSEKEY_ILLEGAL_REQUEST 0x05 #define SENSEKEY_UNIT_ATTENTION 0x06 #define SENSEKEY_DATA_PROTECT 0x07 #define SENSEKEY_BLANK_CHECK 0x08 #define SENSEKEY_VENDOR_SPECIFIC 0x09 #define SENSEKEY_COPY_ABORTED 0x0A #define SENSEKEY_ABORTED_COMMAND 0x0B #define SENSEKEY_EQUAL 0x0C // Obsolete. #define SENSEKEY_VOLUME_OVERFLOW 0x0D #define SENSEKEY_MISCOMPARE 0x0E #define SENSEKEY_RESERVED 0x0F // Data block types (mode page 5). #define DATABLOCK_RAW 0x00 // 2352 bytes raw data. #define DATABLOCK_RAW_PQ 0x01 // Raw data with P and Q Sub-channel. #define DATABLOCK_RAW_PW 0x02 // Raw data with P-W Sub-channel. #define DATABLOCK_RAW_PW_R 0x03 // Raw data with P-W Sub-channel. #define DATABLOCK_MODE1 0x08 // Mode 1 (ISO/IEC 10149): 2048 bytes of user data. #define DATABLOCK_MODE2 0x09 // Mode 2 (ISO/IEC 10149): 2336 bytes of user data. #define DATABLOCK_MODE2_XA 0x0A // Mode 2 (CD-ROM XA, form 1): 2048 bytes of user data, sub-header from write parameters. #define DATABLOCK_MODE2_XA_F1 0x0B // Mode 2 (CD-ROM XA, form 1): 8 bytes of sub-header, 2 048 bytes of user data. #define DATABLOCK_MODE2_XA_F2 0x0C // Mode 2 (CD-ROM XA, form 2): 2324 bytes of user data, sub-header is taken from write parameters. #define DATABLOCK_MODE2_XA_MIX 0x0D // Mode 2 (CD-ROM XA, form 1, form 2, or mixed form): 8 bytes of sub-header, 2324 bytes of user data. ================================================ FILE: src/app/ctrl_messages.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once /* WM_SETDEVICE ------------ Sets the device to the device pointer of lParam. Supported windows: CBurnImageDlg and CCopyDiscDlg. If wParam = 1 when sending to a CCopyDiscDlg window the source device index is set instead of the (default) target device index. */ #define WM_SETDEVICE WM_APP + 0 /* WM_GETDEVICE ------------ Returns the device pointer. Supported windows: CBurnImageDlg and CCopyDiscDlg. If wParam = 1 when sending to a CCopyDiscDlg window the source device index is returned instead of the target device index (which is default). */ #define WM_GETDEVICE WM_APP + 1 /* WM_SETCLONEMODE --------------- Sent to the host of a CCopyDiscGeneralPage class when the clone check box checked. wParam is true if the check box is checked and false if it's unchecked. */ #define WM_SETCLONEMODE WM_APP + 2 /* Messages associated with the CShellListViewCtrl control. */ #define WM_SLVC_BROWSEOBJECT WM_APP + 8 #define WM_SLVC_DONEBROWSEOBJECT WM_APP + 9 #define WM_SLVC_CHANGEFOLDER WM_APP + 10 #define WM_SLVC_CHANGEFOLDERLINK WM_APP + 11 #define WM_SLVC_FILECOMMAND WM_APP + 12 /* WM_CHC_SETSORTCOLUMN -------------------- Set to the CCustomHeaderCtrl object to select which column that should be drawn with a sort arrow. wParams specifies the index of the column and lParam the sort direction (0 for up and 1 for down). */ #define WM_CHC_SETSORTCOLUMN WM_APP + 14 /* WM_SHELLCHANGE -------------- Sent by CDirectoryMonitor when there has been a change in a directory. */ #define WM_SHELLCHANGE WM_APP + 15 /* WM_CONTROLCUSTOMDRAW -------------------- Custom custom draw message sent to a control implementation that needs to be custom drawn. Lparam is a pointer to a NMLVCUSTOMDRAW structure. */ #define WM_CONTROLCUSTOMDRAW WM_APP + 16 /* WM_CHECKMEDIA_BROADCAST ----------------------- Sent to a window parent to make it broad cast a WM_CHECKMEDIA message to all it's children (pages only). lParam is the pointer to the currently selected device. */ #define WM_CHECKMEDIA_BROADCAST WM_APP + 17 /* WM_CHECKMEDIA ------------- Sent to a page whenever the media information should be updated. lParam is the device pointer to the currently selected device. */ #define WM_CHECKMEDIA WM_APP + 18 /* WM_LABELCONTAINER_CLOSE ----------------------- Sent to the host of a label container control when the close button is pressed. */ #define WM_LABELCONTAINER_CLOSE WM_APP + 19 /* Sent to the host of the file system property page when changing the file system. wParam is the previously selected file system and lParam is the file system identifier as defined in Settings.h. */ #define WM_SETFILESYSTEM WM_APP + 20 // Used by class CSpaceMeter. #define WMU_SPACE_METER_DELAYED_UPDATE WM_APP + 21 ================================================ FILE: src/app/dialog/about_window.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include #include #include "resource.h" #include "settings.hh" #include "infrarecorder.hh" #include "version.hh" #include "core.hh" #include "about_window.hh" #define ABOUT_YEARS _T("2006-2012") #define ABOUT_STR(str) str,(sizeof(str)/sizeof(TCHAR))-1 /* * Defines the supported cdrtools versions. These versions are determined by * the CRC-32 checksum of cdrecord.exe. */ typedef struct { ckcore::tuint32 uiChecksum; const TCHAR *szVersion; } tCdrtoolsChecksumVer; size_t g_CdrtoolsChecksumVerCount = 1; tCdrtoolsChecksumVer g_CdrtoolsChecksumVer[1] = { { 0xd47a1004,_T("2.01.01.a61") } }; CAboutWindow::CAboutWindow() : m_VerFont(NULL),m_UrlFont(NULL),m_bUrlHover(false), m_hWndParent(NULL), m_pUpdateLayeredWindow(NULL) { m_VerFont = AtlCreateBoldFont(AtlGetDefaultGuiFont()); LOGFONT lf = { 0 }; if (::GetObject(AtlGetDefaultGuiFont(),sizeof(LOGFONT),&lf) == sizeof(LOGFONT)) { lf.lfUnderline = 1; m_UrlFont = ::CreateFontIndirect(&lf); } if (m_UrlFont == NULL) m_UrlFont = AtlGetDefaultGuiFont(); // Load the function dynamically. HMODULE hUser32 = GetModuleHandle(_T("USER32.DLL")); m_pUpdateLayeredWindow = (tUpdateLayeredWindow)GetProcAddress(hUser32,"UpdateLayeredWindow"); } CAboutWindow::~CAboutWindow() { if (m_VerFont != AtlGetDefaultGuiFont()) ::DeleteObject(m_VerFont); if (m_UrlFont != AtlGetDefaultGuiFont()) ::DeleteObject(m_UrlFont); } void CAboutWindow::UpdateVersionInfo() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); unsigned long ulDummy; unsigned long ulDataSize = GetFileVersionInfoSize(szFileName,&ulDummy); if (ulDataSize != 0) { unsigned char *pBlock = new unsigned char[ulDataSize]; struct LANGANDCODEPAGE { unsigned short usLanguage; unsigned short usCodePage; } *pTranslate; if (GetFileVersionInfo(szFileName,NULL,ulDataSize,pBlock) > 0) { // Get language information (only one language should be present). VerQueryValue(pBlock,_T("\\VarFileInfo\\Translation"), (LPVOID *)&pTranslate,(unsigned int *)&ulDummy); // Calculate the FileVersion sub block path. lsprintf(m_szVersion,_T("\\StringFileInfo\\%04x%04x\\FileVersion"), pTranslate[0].usLanguage,pTranslate[0].usCodePage); unsigned char *pBuffer; VerQueryValue(pBlock,m_szVersion,(LPVOID *)&pBuffer,(unsigned int *)&ulDataSize); // Architecture. #ifdef _M_IA64 TCHAR *szArcStr = _T("IA64"); #elif defined _M_X64 TCHAR *szArcStr = _T("x64"); #else TCHAR *szArcStr = _T("x86"); #endif // Character coding. #ifdef PORTABLE lsprintf(m_szVersion,_T("Version %s portable (unicode, %s)"), (TCHAR *)pBuffer,szArcStr); #else lsprintf(m_szVersion,_T("Version %s (unicode, %s)"), (TCHAR *)pBuffer,szArcStr); #endif } delete [] pBlock; } // Update cdrtools version information. m_szCdrtoolsVersion = _T("Installed version: Unknown"); ckcore::Path CdrecordPath = g_GlobalSettings.m_szCDRToolsPath; CdrecordPath += _T(CORE_WRITEAPP); ckcore::FileInStream CdrecordStream(CdrecordPath); if (!CdrecordStream.open()) return; ckcore::CrcStream CrcStream(ckcore::CrcStream::ckCRC_32); if (!ckcore::stream::copy(CdrecordStream,CrcStream)) return; for (size_t i = 0; i < g_CdrtoolsChecksumVerCount; i++) { if (g_CdrtoolsChecksumVer[i].uiChecksum == CrcStream.checksum()) { m_szCdrtoolsVersion = _T("Installed version: "); m_szCdrtoolsVersion += g_CdrtoolsChecksumVer[i].szVersion; m_szCdrtoolsVersion += _T(" (officially supported)"); break; } } } LRESULT CAboutWindow::OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Load a 32-bit transparent bitmap for Windows 2000 and newer systems. if (m_pUpdateLayeredWindow != NULL) LoadBitmaps(); SIZE sSplashBitmap; m_SplashTmpBitmap.GetSize(sSplashBitmap); SetWindowPos(HWND_TOPMOST,0,0,sSplashBitmap.cx,sSplashBitmap.cy,SWP_NOMOVE); CenterWindow(HWND_DESKTOP); // For per-pixel alpha transparency the window needs to be layered. if (m_pUpdateLayeredWindow != NULL) ModifyStyleEx(0,WS_EX_LAYERED); Render(); return 0; } void CAboutWindow::RollbackBitmap() { BITMAP bmpDstInfo; m_SplashTmpBitmap.GetBitmap(&bmpDstInfo); BITMAP bmbRefInfo; m_SplashRefBitmap.GetBitmap(&bmbRefInfo); unsigned char *pDstDataBits = (unsigned char *)bmpDstInfo.bmBits; unsigned char *pSrcDataBits = (unsigned char *)bmbRefInfo.bmBits; for (int y = 0; y < bmpDstInfo.bmHeight; y++) { unsigned char *pDstPixel = pDstDataBits + bmpDstInfo.bmWidth * 4 * y; unsigned char *pSrcPixel = pSrcDataBits + bmbRefInfo.bmWidth * 4 * y; for (int x = 0; x < bmpDstInfo.bmWidth; x++) { pDstPixel[0] = pSrcPixel[0]; pDstPixel[1] = pSrcPixel[1]; pDstPixel[2] = pSrcPixel[2]; pDstPixel[3] = pSrcPixel[3]; pDstPixel += 4; pSrcPixel += 4; } } } void CAboutWindow::Render() { InvalidateRect(NULL); // Process the message queue. ProcessMessages(); } LRESULT CAboutWindow::OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CPaintDC dc(m_hWnd); if (m_pUpdateLayeredWindow == NULL) return 0; RECT rcClient; GetClientRect(&rcClient); // FIXME: I have a good feeling that there is a much more efficient way to // achieve the requested behavior without manually copying the // reference bitmap. RollbackBitmap(); HDC hMemDC = CreateCompatibleDC(dc); HBITMAP hOldBitmap = (HBITMAP)SelectObject(hMemDC,m_SplashTmpBitmap); RECT rcVersion = { 37,115,390,145 }; DrawText(hMemDC,m_VerFont,&rcVersion,ABOUTWINDOW_TEXTCOLOR, m_szVersion,lstrlen(m_szVersion)); RECT rcCopyright = { 37,145,390,175 }; DrawText(hMemDC,AtlGetDefaultGuiFont(),&rcCopyright,ABOUTWINDOW_TEXTCOLOR, ABOUT_STR(_T("Copyright ") ABOUT_YEARS _T(" Christian Kindahl."))); RECT rcLegal = { 37,175,390,300 }; DrawText(hMemDC,AtlGetDefaultGuiFont(),&rcLegal,ABOUTWINDOW_TEXTCOLOR, ABOUT_STR(_T("InfraRecorder comes with absolutely no warranty. ") _T("This is free software, and you are welcome to ") _T("redistribute it under certain conditions; please ") _T("see License.txt for more information."))); RECT rcThanks = { 37,230,390,260 }; DrawText(hMemDC,AtlGetDefaultGuiFont(),&rcThanks,ABOUTWINDOW_TEXTCOLOR, ABOUT_STR(_T("Special thanks to R. Diez for his contributions."))); RECT rcCdrtools = { 37,260,390,320 }; DrawText(hMemDC,AtlGetDefaultGuiFont(),&rcCdrtools,ABOUTWINDOW_TEXTCOLOR, ABOUT_STR(_T("InfraRecorder uses cdrecord, readcd and cdda2wav from ") _T("the cdrtools software suite. cdrtools copyright ") _T("1995-2009 Jrg Schilling."))); RECT rcCdrtoolsVer = { 37,300,390,330 }; DrawText(hMemDC,AtlGetDefaultGuiFont(),&rcCdrtoolsVer,ABOUTWINDOW_TEXTCOLOR, m_szCdrtoolsVersion.c_str(),static_cast(m_szCdrtoolsVersion.size())); RECT rcUrl = { ABOUTWINDOW_URL_LEFT,ABOUTWINDOW_URL_TOP, ABOUTWINDOW_URL_RIGHT,ABOUTWINDOW_URL_BOTTOM }; DrawText(hMemDC,m_bUrlHover ? m_UrlFont : AtlGetDefaultGuiFont(), &rcUrl,ABOUTWINDOW_URLCOLOR, ABOUT_STR(_T("http://infrarecorder.org"))); DrawBitmap(dc,hMemDC); SelectObject(hMemDC,hOldBitmap); ReleaseDC(dc); ReleaseDC(hMemDC); return 0; } void CAboutWindow::DrawBitmap(HDC hScreenDC,HDC hMemDC) { SIZE sSplashBitmap; m_SplashTmpBitmap.GetSize(sSplashBitmap); // Calculate window dimensions. RECT rcWindow; GetWindowRect(&rcWindow); POINT ptWindowPos; ptWindowPos.x = rcWindow.left; ptWindowPos.y = rcWindow.top; BLENDFUNCTION bfPixelFunction = { AC_SRC_OVER,0,255,AC_SRC_ALPHA }; POINT ptSource = { 0,0 }; m_pUpdateLayeredWindow(m_hWnd,hScreenDC,&ptWindowPos,&sSplashBitmap, hMemDC,&ptSource,0,&bfPixelFunction,ULW_ALPHA); } void CAboutWindow::DrawText(HDC hDC,HFONT hFont,RECT *pRect, COLORREF Color,const TCHAR *szText, int iTextLen) { HFONT hOldFont = (HFONT)SelectObject(hDC,hFont); ::SetBkMode(hDC,TRANSPARENT); ::SetTextColor(hDC,Color); ::DrawText(hDC,szText,iTextLen,pRect, DT_LEFT | DT_END_ELLIPSIS | DT_WORDBREAK); SelectObject(hDC,hOldFont); // Get bitmap information. BITMAP bmpInfo; m_SplashTmpBitmap.GetBitmap(&bmpInfo); // Since the regular GDI functions (with a few exceptions) clear the alpha bit // when they are used we need to set it, since we don't want to draw // transparent text. unsigned char *pDataBits = (unsigned char *)bmpInfo.bmBits; int iStart = bmpInfo.bmHeight - pRect->bottom; int iEnd = bmpInfo.bmHeight - pRect->top; for (int y = iStart; y < iEnd; y++) { unsigned char *pPixel = pDataBits + bmpInfo.bmWidth * 4 * y; pPixel += 4 * pRect->left; for (int x = pRect->left; x < pRect->right; x++) { pPixel[3] = 0xFF; pPixel += 4; } } } /** * Utility function for loading the layered alpha bitmap into the specified * bitmap object. * @param [out] Bitmap The bitmap object to load the image into. */ void CAboutWindow::LoadBitmap(CBitmap &Bitmap) { // Load the bitmap. HBITMAP hBitmap = (HBITMAP)LoadImage(_Module.GetModuleInstance(),MAKEINTRESOURCE(IDB_ABOUTBITMAP), IMAGE_BITMAP,0,0,LR_CREATEDIBSECTION); Bitmap.Attach(hBitmap); // Precaclulate multiply the transparency. BITMAP bmpInfo; Bitmap.GetBitmap(&bmpInfo); unsigned char *pDataBits = (unsigned char *)bmpInfo.bmBits; for (int y = 0; y < bmpInfo.bmHeight; y++) { unsigned char *pPixel = pDataBits + bmpInfo.bmWidth * 4 * y; for (int x = 0; x < bmpInfo.bmWidth; x++) { pPixel[0] = pPixel[0] * pPixel[3] / 255; pPixel[1] = pPixel[1] * pPixel[3] / 255; pPixel[2] = pPixel[2] * pPixel[3] / 255; pPixel += 4; } } } void CAboutWindow::LoadBitmaps() { LoadBitmap(m_SplashTmpBitmap); LoadBitmap(m_SplashRefBitmap); } LRESULT CAboutWindow::OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { int iPosX = GET_X_LPARAM(lParam); int iPosY = GET_Y_LPARAM(lParam); if (iPosX > ABOUTWINDOW_URL_LEFT && iPosX < ABOUTWINDOW_URL_RIGHT && iPosY > ABOUTWINDOW_URL_TOP && iPosY < ABOUTWINDOW_URL_BOTTOM) { if (g_WinVer.m_ulMajorVersion >= MAJOR_WIN2000 && GetCursor() != LoadCursor(NULL,IDC_HAND)) { SetCursor(LoadCursor(NULL,IDC_HAND)); } bool bRender = !m_bUrlHover; m_bUrlHover = true; if (bRender) Render(); } else { if (GetCursor() != LoadCursor(NULL,IDC_ARROW)) SetCursor(LoadCursor(NULL,IDC_ARROW)); bool bRender = m_bUrlHover; m_bUrlHover = false; if (bRender) Render(); } return 0; } LRESULT CAboutWindow::OnLButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { int iPosX = GET_X_LPARAM(lParam); int iPosY = GET_Y_LPARAM(lParam); if (iPosX > ABOUTWINDOW_URL_LEFT && iPosX < ABOUTWINDOW_URL_RIGHT && iPosY > ABOUTWINDOW_URL_TOP && iPosY < ABOUTWINDOW_URL_BOTTOM) { ::ShellExecute(m_hWnd,_T("open"),_T("http://infrarecorder.org"), NULL,NULL,SW_SHOW); } // Re-enable the parent window. if (m_hWndParent != NULL) ::EnableWindow(m_hWndParent,TRUE); DestroyWindow(); return 0; } void CAboutWindow::CreateAndShow(HWND hWndParent) { UpdateVersionInfo(); // Windows 2000+ users may enjoy a real about Window while the others will // have a simple message box for compatibility. if (m_pUpdateLayeredWindow != NULL) { // Disable the parent window. m_hWndParent = hWndParent; ::EnableWindow(m_hWndParent,FALSE); Create(hWndParent,CWindow::rcDefault); ShowWindow(true); Render(); } else { ckcore::tstring Message = m_szVersion; Message += _T(" copyright ") ABOUT_YEARS _T(" Christian Kindahl.\n\n"); Message += _T("Please visit http://infrarecorder.org for more information."); ::MessageBox(hWndParent,Message.c_str(),_T("About InfraRecorder"), MB_OK | MB_ICONINFORMATION); } } ================================================ FILE: src/app/dialog/about_window.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #define ABOUTWINDOW_TEXTCOLOR RGB(50,50,50) #define ABOUTWINDOW_URLCOLOR RGB(51,100,163) #define ABOUTWINDOW_URL_LEFT 37 #define ABOUTWINDOW_URL_TOP 343 #define ABOUTWINDOW_URL_RIGHT 150 #define ABOUTWINDOW_URL_BOTTOM 373 #if (_WIN32_WINNT < 0x0500) #define WS_EX_LAYERED 0x00080000 #define ULW_ALPHA 0x00000002 #endif #ifndef IDC_HAND #define IDC_HAND MAKEINTRESOURCE(32649) #endif typedef BOOL (WINAPI *tUpdateLayeredWindow)(HWND hWnd,HDC hdcDst,POINT *pptDst, SIZE *psize,HDC hdcSrc,POINT *pptSrc, COLORREF crKey,BLENDFUNCTION *pblend, DWORD dwFlags); class CAboutWindow : public CWindowImpl > { private: CBitmap m_SplashTmpBitmap; CBitmap m_SplashRefBitmap; HFONT m_VerFont; HFONT m_UrlFont; bool m_bUrlHover; // Updated by the UpdateVersionInfo function. TCHAR m_szVersion[128]; ckcore::tstring m_szCdrtoolsVersion; HWND m_hWndParent; void UpdateVersionInfo(); void RollbackBitmap(); void Render(); tUpdateLayeredWindow m_pUpdateLayeredWindow; void DrawBitmap(HDC hScreenDC,HDC hMemDC); void DrawText(HDC hDC,HFONT hFont,RECT *pRect,COLORREF Color, const TCHAR *szText,int iTextLen); void LoadBitmap(CBitmap &Bitmap); void LoadBitmaps(); public: CAboutWindow(); ~CAboutWindow(); BEGIN_MSG_MAP(CAboutWindow) MESSAGE_HANDLER(WM_CREATE,OnCreate) MESSAGE_HANDLER(WM_PAINT,OnPaint) MESSAGE_HANDLER(WM_MOUSEMOVE,OnMouseMove); MESSAGE_HANDLER(WM_LBUTTONDOWN,OnLButtonDown) END_MSG_MAP() LRESULT OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnLButtonDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); void CreateAndShow(HWND hWndParent); }; extern CAboutWindow *g_pAboutWnd; ================================================ FILE: src/app/dialog/add_boot_image_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "add_boot_image_dlg.hh" #include "string_table.hh" #include "lang_util.hh" /* CAddBootImageDlg::CAddBootImageDlg ---------------------------------- bEdit detemines if the title should state than a boot image is beeing edited or if we're adding a new boot image to the project. It also determines if the path edit should be enabled. */ CAddBootImageDlg::CAddBootImageDlg(CProjectBootImage *pBootImage,bool bEdit) { m_bEdit = bEdit; m_pBootImage = pBootImage; } CAddBootImageDlg::~CAddBootImageDlg() { } bool CAddBootImageDlg::Translate() { // Set the title. if (m_bEdit) SetWindowText(lngGetString(TITLE_EDITBOOTIMAGE)); if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a addbootimage translation section. if (!pLng->EnterSection(_T("addbootimage"))) return false; TCHAR *szStrValue; // Set the title. if (!m_bEdit) { if (pLng->GetValuePtr(IDD_ADDBOOTIMAGEDLG,szStrValue)) SetWindowText(szStrValue); } // Translate the rest. if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDC_HELPBUTTON,szStrValue)) SetDlgItemText(IDC_HELPBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_EMULATIONSTATIC,szStrValue)) SetDlgItemText(IDC_EMULATIONSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_OPTIONSSTATIC,szStrValue)) SetDlgItemText(IDC_OPTIONSSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_NOBOOTCHECK,szStrValue)) SetDlgItemText(IDC_NOBOOTCHECK,szStrValue); if (pLng->GetValuePtr(IDC_BOOTSEGMENTSTATIC,szStrValue)) SetDlgItemText(IDC_BOOTSEGMENTSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_BOOTSIZESTATIC,szStrValue)) SetDlgItemText(IDC_BOOTSIZESTATIC,szStrValue); return true; } LRESULT CAddBootImageDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); // Set edit field length limit. ::SendMessage(GetDlgItem(IDC_BOOTSEGMENTEDIT),EM_SETLIMITTEXT,MAX_BOOTLOAD_SIZE - 1,0); ::SendMessage(GetDlgItem(IDC_BOOTSIZEEDIT),EM_SETLIMITTEXT,MAX_BOOTLOAD_SIZE - 1,0); // Initialize the emulation combo box. m_EmuCombo = GetDlgItem(IDC_EMULATIONCOMBO); m_EmuCombo.AddString(lngGetString(BOOTEMU_NONE)); m_EmuCombo.AddString(lngGetString(BOOTEMU_FLOPPY)); m_EmuCombo.AddString(lngGetString(BOOTEMU_HARDDISK)); m_EmuCombo.SetCurSel(m_pBootImage->m_iEmulation); BOOL bDummy; OnEmuChange(NULL,NULL,NULL,bDummy); // Setup the default settings. CheckDlgButton(IDC_NOBOOTCHECK,m_pBootImage->m_bNoBoot); TCHAR szBuffer[32]; lsnprintf_s(szBuffer,32,_T("0x%x"),m_pBootImage->m_uiLoadSegment); SetDlgItemText(IDC_BOOTSEGMENTEDIT,szBuffer); lsnprintf_s(szBuffer,32,_T("0x%x"),m_pBootImage->m_uiLoadSize); SetDlgItemText(IDC_BOOTSIZEEDIT,szBuffer); // Translate the window. Translate(); return TRUE; } LRESULT CAddBootImageDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Copy all information over to the CProjectBootImage object. m_pBootImage->m_iEmulation = m_EmuCombo.GetCurSel(); m_pBootImage->m_bNoBoot = IsDlgButtonChecked(IDC_NOBOOTCHECK) == TRUE; TCHAR szBuffer[MAX_BOOTLOAD_SIZE]; GetDlgItemText(IDC_BOOTSEGMENTEDIT,szBuffer,MAX_BOOTLOAD_SIZE - 1); lsscanf(szBuffer,_T("0x%x"),&m_pBootImage->m_uiLoadSegment); GetDlgItemText(IDC_BOOTSIZEEDIT,szBuffer,MAX_BOOTLOAD_SIZE - 1); lsscanf(szBuffer,_T("0x%x"),&m_pBootImage->m_uiLoadSize); TCHAR szTemp[32]; lsprintf(szTemp,_T("%d %d"),m_pBootImage->m_uiLoadSegment,m_pBootImage->m_uiLoadSize); EndDialog(wID); return FALSE; } LRESULT CAddBootImageDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } LRESULT CAddBootImageDlg::OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/working_with_projects/add_boot_image.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); return 0; } LRESULT CAddBootImageDlg::OnEmuChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (m_EmuCombo.GetCurSel() == PROJECTBI_BOOTEMU_NONE) { ::EnableWindow(GetDlgItem(IDC_NOBOOTCHECK),FALSE); ::EnableWindow(GetDlgItem(IDC_BOOTSEGMENTSTATIC),TRUE); ::EnableWindow(GetDlgItem(IDC_BOOTSEGMENTEDIT),TRUE); ::EnableWindow(GetDlgItem(IDC_BOOTSIZESTATIC),TRUE); ::EnableWindow(GetDlgItem(IDC_BOOTSIZEEDIT),TRUE); } else { ::EnableWindow(GetDlgItem(IDC_NOBOOTCHECK),TRUE); ::EnableWindow(GetDlgItem(IDC_BOOTSEGMENTSTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_BOOTSEGMENTEDIT),FALSE); ::EnableWindow(GetDlgItem(IDC_BOOTSIZESTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_BOOTSIZEEDIT),FALSE); } return 0; } ================================================ FILE: src/app/dialog/add_boot_image_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "settings.hh" class CAddBootImageDlg : public CDialogImpl { private: bool m_bEdit; CProjectBootImage *m_pBootImage; CComboBox m_EmuCombo; enum { MAX_BOOTLOAD_SIZE = 32 }; bool Translate(); public: enum { IDD = IDD_ADDBOOTIMAGEDLG }; CAddBootImageDlg(CProjectBootImage *pBootImage,bool bEdit); ~CAddBootImageDlg(); BEGIN_MSG_MAP(CAddBootImageDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) COMMAND_ID_HANDLER(IDC_HELPBUTTON,OnHelp) COMMAND_HANDLER(IDC_EMULATIONCOMBO,CBN_SELCHANGE,OnEmuChange) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnEmuChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/burn_advanced_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "burn_advanced_page.hh" #include "ctrl_messages.hh" #include "cdrtools_parse_strings.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" CBurnAdvancedPage::CBurnAdvancedPage() { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_ADVANCED,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CBurnAdvancedPage::~CBurnAdvancedPage() { Detach(); } bool CBurnAdvancedPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a burn translation section. if (!pLng->EnterSection(_T("burn"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_OVERBURNCHECK,szStrValue)) SetDlgItemText(IDC_OVERBURNCHECK,szStrValue); if (pLng->GetValuePtr(IDC_SWABCHECK,szStrValue)) SetDlgItemText(IDC_SWABCHECK,szStrValue); if (pLng->GetValuePtr(IDC_IGNORESIZECHECK,szStrValue)) SetDlgItemText(IDC_IGNORESIZECHECK,szStrValue); if (pLng->GetValuePtr(IDC_IMMEDCHECK,szStrValue)) SetDlgItemText(IDC_IMMEDCHECK,szStrValue); if (pLng->GetValuePtr(IDC_AUDIOMASTERCHECK,szStrValue)) SetDlgItemText(IDC_AUDIOMASTERCHECK,szStrValue); if (pLng->GetValuePtr(IDC_FORCESPEEDCHECK,szStrValue)) SetDlgItemText(IDC_FORCESPEEDCHECK,szStrValue); if (pLng->GetValuePtr(IDC_VARIRECCHECK,szStrValue)) SetDlgItemText(IDC_VARIRECCHECK,szStrValue); return true; } bool CBurnAdvancedPage::OnApply() { // Remember the configuration. g_BurnAdvancedSettings.m_bOverburn = IsDlgButtonChecked(IDC_OVERBURNCHECK) == TRUE; g_BurnAdvancedSettings.m_bSwab = IsDlgButtonChecked(IDC_SWABCHECK) == TRUE; g_BurnAdvancedSettings.m_bIgnoreSize = IsDlgButtonChecked(IDC_IGNORESIZECHECK) == TRUE; g_BurnAdvancedSettings.m_bImmed = IsDlgButtonChecked(IDC_IMMEDCHECK) == TRUE; g_BurnAdvancedSettings.m_bAudioMaster = IsDlgButtonChecked(IDC_AUDIOMASTERCHECK) == TRUE; g_BurnAdvancedSettings.m_bForceSpeed = IsDlgButtonChecked(IDC_FORCESPEEDCHECK) == TRUE; g_BurnAdvancedSettings.m_bVariRec = IsDlgButtonChecked(IDC_VARIRECCHECK) == TRUE; g_BurnAdvancedSettings.m_iVariRec = m_VariRecTrackBar.GetPos(); return true; } void CBurnAdvancedPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/burn_options.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CBurnAdvancedPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // VariRec. m_VariRecTrackBar = GetDlgItem(IDC_VARIRECSLIDER); m_VariRecTrackBar.SetRange(-2,2); m_VariRecTrackBar.SetTipSide(TBTS_BOTTOM); // Setup the default settings. CheckDlgButton(IDC_OVERBURNCHECK,g_BurnAdvancedSettings.m_bOverburn); CheckDlgButton(IDC_SWABCHECK,g_BurnAdvancedSettings.m_bSwab); CheckDlgButton(IDC_IGNORESIZECHECK,g_BurnAdvancedSettings.m_bIgnoreSize); CheckDlgButton(IDC_IMMEDCHECK,g_BurnAdvancedSettings.m_bImmed); CheckDlgButton(IDC_AUDIOMASTERCHECK,g_BurnAdvancedSettings.m_bAudioMaster); CheckDlgButton(IDC_FORCESPEEDCHECK,g_BurnAdvancedSettings.m_bForceSpeed); CheckDlgButton(IDC_VARIRECCHECK,g_BurnAdvancedSettings.m_bVariRec); m_VariRecTrackBar.SetPos(g_BurnAdvancedSettings.m_iVariRec); TCHAR szVariRec[16]; lsprintf(szVariRec,_T("%d"),m_VariRecTrackBar.GetPos()); SetDlgItemText(IDC_VARIRECEDIT,szVariRec); // Translate the window. Translate(); return TRUE; } LRESULT CBurnAdvancedPage::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if ((BOOL)wParam == TRUE) { ckmmc::Device *pDevice = reinterpret_cast(::SendMessage(GetParent(),WM_GETDEVICE,0,0)); ::EnableWindow(GetDlgItem(IDC_SWABCHECK),TRUE); ::EnableWindow(GetDlgItem(IDC_AUDIOMASTERCHECK), pDevice->support(ckmmc::Device::ckDEVICE_AUDIO_MASTER)); ::EnableWindow(GetDlgItem(IDC_FORCESPEEDCHECK), pDevice->support(ckmmc::Device::ckDEVICE_FORCE_SPEED)); bool bVariRec = pDevice->support(ckmmc::Device::ckDEVICE_VARIREC); ::EnableWindow(GetDlgItem(IDC_VARIRECCHECK),bVariRec); ::EnableWindow(GetDlgItem(IDC_VARIRECSLIDER),bVariRec); } bHandled = FALSE; return 0; } LRESULT CBurnAdvancedPage::OnHScroll(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (wParam == TB_ENDTRACK) { TCHAR szPos[16]; lsprintf(szPos,_T("%d"),m_VariRecTrackBar.GetPos()); SetDlgItemText(IDC_VARIRECEDIT,szPos); } bHandled = FALSE; return 0; } ================================================ FILE: src/app/dialog/burn_advanced_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CBurnAdvancedPage : public CPropertyPageImpl { private: CTrackBarCtrl m_VariRecTrackBar; bool Translate(); public: enum { IDD = IDD_PROPPAGE_BURNIMAGEADVANCED }; CBurnAdvancedPage(); ~CBurnAdvancedPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CBurnAdvancedPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) MESSAGE_HANDLER(WM_HSCROLL,OnHScroll) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnHScroll(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/burn_image_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "burn_image_dlg.hh" CBurnImageDlg::CBurnImageDlg(const TCHAR *szTitle,bool bImageHasTOC, bool bEnableOnFly,bool bEnableVerify, bool bAppMode) : m_bCentered(false),m_bAppMode(bAppMode),m_pDevice(NULL), CPropertySheetImpl(szTitle,0,NULL), m_GeneralPage(bImageHasTOC,bEnableOnFly,bEnableVerify) { m_psh.dwFlags |= PSH_NOAPPLYNOW | PSH_HASHELP | PSH_NOCONTEXTHELP; AddPage(m_GeneralPage); AddPage(m_AdvancedPage); } CBurnImageDlg::~CBurnImageDlg() { } LRESULT CBurnImageDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } // Add the dialog to the task bar and enable it to be minimized. if (m_bAppMode) { ModifyStyle(0,WS_MINIMIZEBOX | WS_SYSMENU); ModifyStyleEx(0,WS_EX_APPWINDOW); HMENU hSysMenu = GetSystemMenu(FALSE); ::InsertMenu(hSysMenu,0,MF_BYPOSITION,SC_RESTORE,_T("&Restore")); ::InsertMenu(hSysMenu,2,MF_BYPOSITION,SC_MINIMIZE,_T("Mi&nimize")); ::InsertMenu(hSysMenu,3,MF_BYPOSITION | MF_SEPARATOR,0,_T("")); } bHandled = FALSE; return 0; } LRESULT CBurnImageDlg::OnSetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_pDevice = reinterpret_cast(lParam); bHandled = TRUE; return 0; } LRESULT CBurnImageDlg::OnGetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { bHandled = TRUE; return reinterpret_cast(m_pDevice); } ================================================ FILE: src/app/dialog/burn_image_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "burn_image_general_page.hh" #include "burn_advanced_page.hh" #include "ctrl_messages.hh" class CBurnImageDlg : public CPropertySheetImpl { private: bool m_bCentered; bool m_bAppMode; ckmmc::Device *m_pDevice; CBurnImageGeneralPage m_GeneralPage; CBurnAdvancedPage m_AdvancedPage; public: CBurnImageDlg(const TCHAR *szTitle,bool bImageHasTOC, bool bEnableOnFly,bool bEnableVerify,bool bAppMode); ~CBurnImageDlg(); BEGIN_MSG_MAP(CBurnImageDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) MESSAGE_HANDLER(WM_SETDEVICE,OnSetDevice) MESSAGE_HANDLER(WM_GETDEVICE,OnGetDevice) CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnGetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/burn_image_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "infrarecorder.hh" #include "ctrl_messages.hh" #include "cdrtools_parse_strings.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" #include "info_dlg.hh" #include "trans_util.hh" #include "device_util.hh" #include "core2_util.hh" #include "version.hh" #include "visual_styles.hh" #include "burn_image_general_page.hh" CBurnImageGeneralPage::CBurnImageGeneralPage(bool bImageHasTOC,bool bEnableOnFly, bool bEnableVerify) { m_bImageHasTOC = bImageHasTOC; m_bEnableOnFly = bEnableOnFly; m_bEnableVerify = bEnableVerify; m_uiParentTitleLen = 0; m_hIcon = NULL; m_hRefreshIcon = NULL; m_hRefreshImageList = NULL; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_GENERAL,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CBurnImageGeneralPage::~CBurnImageGeneralPage() { if (m_hRefreshImageList != NULL) ImageList_Destroy(m_hRefreshImageList); if (m_hRefreshIcon != NULL) DestroyIcon(m_hRefreshIcon); if (m_hIcon != NULL) DestroyIcon(m_hIcon); } bool CBurnImageGeneralPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a burn translation section. if (!pLng->EnterSection(_T("burn"))) return false; // Translate. TCHAR *szStrValue; int iMaxStaticRight = 0; if (pLng->GetValuePtr(IDC_WRITESPEEDSTATIC,szStrValue)) { SetDlgItemText(IDC_WRITESPEEDSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_WRITESPEEDSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_WRITEMETHODSTATIC,szStrValue)) { SetDlgItemText(IDC_WRITEMETHODSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_WRITEMETHODSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_NUMCOPIESSTATIC,szStrValue)) { SetDlgItemText(IDC_NUMCOPIESSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_NUMCOPIESSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_EJECTCHECK,szStrValue)) SetDlgItemText(IDC_EJECTCHECK,szStrValue); if (pLng->GetValuePtr(IDC_SIMULATECHECK,szStrValue)) SetDlgItemText(IDC_SIMULATECHECK,szStrValue); if (pLng->GetValuePtr(IDC_BUPCHECK,szStrValue)) SetDlgItemText(IDC_BUPCHECK,szStrValue); if (pLng->GetValuePtr(IDC_PADCHECK,szStrValue)) SetDlgItemText(IDC_PADCHECK,szStrValue); if (pLng->GetValuePtr(IDC_FIXATECHECK,szStrValue)) SetDlgItemText(IDC_FIXATECHECK,szStrValue); if (pLng->GetValuePtr(IDC_VERIFYCHECK,szStrValue)) SetDlgItemText(IDC_VERIFYCHECK,szStrValue); // Borrow the on the fly translation from the copy dialog. if (!pLng->EnterSection(_T("copy"))) return false; if (pLng->GetValuePtr(IDC_ONFLYCHECK,szStrValue)) SetDlgItemText(IDC_ONFLYCHECK,szStrValue); // Make sure that the edit controls are not in the way of the statics. if (iMaxStaticRight > 75) { UpdateEditPos(m_hWnd,IDC_WRITESPEEDCOMBO,iMaxStaticRight,true); UpdateEditPos(m_hWnd,IDC_WRITEMETHODCOMBO,iMaxStaticRight,true); } return true; } bool CBurnImageGeneralPage::InitRecorderMedia() { if (m_uiParentTitleLen == 0) m_uiParentTitleLen = GetParentWindow(this).GetWindowTextLength(); TCHAR szBuffer[256]; GetParentWindow(this).GetWindowText(szBuffer,m_uiParentTitleLen + 1); // Obtain the device. ckmmc::Device &Device = *reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); Device.refresh(); // Get current profile. ckmmc::Device::Profile Profile = Device.profile(); // Note: On CD-R/RW media the Test Write bit is valid only for Write Type // 1 or 2 (Track at Once or Session at Once). On DVD-R media, the Test // Write bit is valid only for Write Type 0 or 2 (Incremental or // Disc-at-once). This is completely disregarded at the moment. bool bSupportedProfile = false; switch (Profile) { case ckmmc::Device::ckPROFILE_DVDRAM: case ckmmc::Device::ckPROFILE_DVDPLUSRW: case ckmmc::Device::ckPROFILE_DVDPLUSRW_DL: case ckmmc::Device::ckPROFILE_DVDMINUSRW_RESTOV: case ckmmc::Device::ckPROFILE_DVDMINUSRW_SEQ: case ckmmc::Device::ckPROFILE_DVDPLUSR: case ckmmc::Device::ckPROFILE_DVDPLUSR_DL: // Not sure about these: case ckmmc::Device::ckPROFILE_BDROM: case ckmmc::Device::ckPROFILE_BDR_SRM: case ckmmc::Device::ckPROFILE_BDR_RRM: case ckmmc::Device::ckPROFILE_BDRE: case ckmmc::Device::ckPROFILE_HDDVDROM: case ckmmc::Device::ckPROFILE_HDDVDR: case ckmmc::Device::ckPROFILE_HDDVDRAM: bSupportedProfile = true; // Disable simulation (not supported for DVD+RW media). ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK),FALSE); break; case ckmmc::Device::ckPROFILE_CDR: case ckmmc::Device::ckPROFILE_CDRW: case ckmmc::Device::ckPROFILE_DVDMINUSR_SEQ: case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_SEQ: case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_JUMP: bSupportedProfile = true; // Enable simulation if supported by recorder. ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK), Device.support(ckmmc::Device::ckDEVICE_TEST_WRITE)); break; case ckmmc::Device::ckPROFILE_NONE: lstrcat(szBuffer,_T(" ")); lstrcat(szBuffer,lngGetString(MEDIA_INSERTBLANK)); break; default: lstrcat(szBuffer,_T(" ")); lstrcat(szBuffer,lngGetString(MEDIA_UNSUPPORTED)); break; } GetParentWindow(this).SetWindowText(szBuffer); if (bSupportedProfile) { // Maximum write speed. m_WriteSpeedCombo.ResetContent(); m_WriteSpeedCombo.AddString(lngGetString(MISC_MAXIMUM)); m_WriteSpeedCombo.SetItemData(0,static_cast(-1)); m_WriteSpeedCombo.SetCurSel(0); // Other supported write speeds. const std::vector &WriteSpeeds = Device.write_speeds(); std::vector::const_iterator it; for (it = WriteSpeeds.begin(); it != WriteSpeeds.end(); it++) { m_WriteSpeedCombo.AddString(ckmmc::util::kb_to_disp_speed(*it,Profile).c_str()); m_WriteSpeedCombo.SetItemData(m_WriteSpeedCombo.GetCount() - 1, static_cast(ckmmc::util::kb_to_human_speed(*it, /*ckmmc::Device::ckPROFILE_CDR*/Profile))); } // Write modes. m_WriteMethodCombo.ResetContent(); if (Device.support(ckmmc::Device::ckWM_SAO)) m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_SAO)); if (Device.support(ckmmc::Device::ckWM_TAO)) { m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_TAO)); m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_TAONOPREGAP)); } if (Device.support(ckmmc::Device::ckWM_RAW96R)) m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_RAW96R)); if (Device.support(ckmmc::Device::ckWM_RAW16)) m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_RAW16)); if (Device.support(ckmmc::Device::ckWM_RAW96P)) m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_RAW96P)); m_WriteMethodCombo.SetCurSel(0); } else { return false; } return true; } void CBurnImageGeneralPage::SuggestWriteMethod() { ckmmc::Device &Device = *reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); // Suggest the best raw write method if the image has an associated TOC file. if (m_bImageHasTOC) { // Check for supported write modes. Raw96r has the highest priority, if // that's not support the raw16 mode is recommended, if none of the mentioned // write modes are supported a warning message is displayed. int uiStrID = -1; if (Device.support(ckmmc::Device::ckWM_RAW96R)) uiStrID = WRITEMODE_RAW96R; else if (Device.support(ckmmc::Device::ckWM_RAW16)) uiStrID = WRITEMODE_RAW16; const TCHAR *szStr = lngGetString(uiStrID); if (uiStrID != -1) { TCHAR szItemText[128]; for (int i = 0; i < m_WriteMethodCombo.GetCount(); i++) { if (m_WriteMethodCombo.GetLBTextLen(i) >= (sizeof(szItemText) / sizeof(TCHAR))) continue; m_WriteMethodCombo.GetLBText(i,szItemText); if (!lstrcmp(szItemText,szStr)) { m_WriteMethodCombo.SetCurSel(i); break; } } } else { // No good raw writing mode found. MessageBox(lngGetString(WARNING_CLONEWRITEMETHOD),lngGetString(GENERAL_WARNING), MB_OK | MB_ICONWARNING); } } else if (g_ProjectSettings.m_bMultiSession) { // Suggest the TAO write mode for multi-session discs if available. if (Device.support(ckmmc::Device::ckWM_TAO)) { const TCHAR *szStr = lngGetString(WRITEMODE_TAO); TCHAR szItemText[128]; for (int i = 0; i < m_WriteMethodCombo.GetCount(); i++) { if (m_WriteMethodCombo.GetLBTextLen(i) >= (sizeof(szItemText) / sizeof(TCHAR))) continue; m_WriteMethodCombo.GetLBText(i,szItemText); if (!lstrcmp(szItemText,szStr)) { m_WriteMethodCombo.SetCurSel(i); break; } } } } } void CBurnImageGeneralPage::InitRefreshButton() { m_hRefreshIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_REFRESHICON),IMAGE_ICON,16,16,LR_DEFAULTCOLOR); // In Windows XP there is a bug causing the button to loose it's themed style if // assigned an icon. The solution to this is to assign an image list instead. if (g_WinVer.m_ulMajorCCVersion >= 6) { // Get color depth (minimum requirement is 32-bits for alpha blended images). int iBitsPixel = GetDeviceCaps(::GetDC(HWND_DESKTOP),BITSPIXEL); m_hRefreshImageList = ImageList_Create(16,16,ILC_COLOR32 | (iBitsPixel < 32 ? ILC_MASK : 0),0,1); ImageList_AddIcon(m_hRefreshImageList,m_hRefreshIcon); BUTTON_IMAGELIST bImageList; bImageList.himl = m_hRefreshImageList; bImageList.margin.left = 0; bImageList.margin.top = 0; bImageList.margin.right = 0; bImageList.margin.bottom = 0; bImageList.uAlign = BUTTON_IMAGELIST_ALIGN_CENTER; SendMessage(GetDlgItem(IDC_REFRESHBUTTON),BCM_SETIMAGELIST,0,(LPARAM)&bImageList); } else { SendMessage(GetDlgItem(IDC_REFRESHBUTTON),BM_SETIMAGE,IMAGE_ICON,(LPARAM)m_hRefreshIcon); } // If the application is themed, then adjust the size of the button. if (g_VisualStyles.IsThemeActive()) { RECT rcButton; ::GetWindowRect(GetDlgItem(IDC_REFRESHBUTTON),&rcButton); ScreenToClient(&rcButton); ::SetWindowPos(GetDlgItem(IDC_REFRESHBUTTON),NULL,rcButton.left - 1,rcButton.top - 1, rcButton.right - rcButton.left + 2,rcButton.bottom - rcButton.top + 2,0); } } void CBurnImageGeneralPage::CheckRecorderMedia() { // Check that we have a recorder in the system. if (m_RecorderCombo.GetItemData(m_RecorderCombo.GetCurSel()) == 0) return; bool bMediaInit = InitRecorderMedia(); if (!bMediaInit) { // Write speed. m_WriteSpeedCombo.ResetContent(); m_WriteSpeedCombo.AddString(lngGetString(MISC_MAXIMUM)); m_WriteSpeedCombo.SetCurSel(0); // Write method. m_WriteMethodCombo.ResetContent(); m_WriteMethodCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_WriteMethodCombo.SetCurSel(0); } m_WriteSpeedCombo.EnableWindow(bMediaInit); m_WriteMethodCombo.EnableWindow(bMediaInit); ::EnableWindow(::GetDlgItem(GetParent(),IDOK),bMediaInit); ::EnableWindow(GetDlgItem(IDC_WRITESPEEDSTATIC),bMediaInit); ::EnableWindow(GetDlgItem(IDC_WRITEMETHODSTATIC),bMediaInit); // Suggest a write method. SuggestWriteMethod(); } bool CBurnImageGeneralPage::OnApply() { // Verify the number of copies. TCHAR szNumCopies[64]; m_NumCopiesCombo.GetWindowText(szNumCopies,sizeof(szNumCopies) / sizeof(TCHAR) -1); long lNumCopies = 1; if (lsscanf(szNumCopies,_T("%d"),&lNumCopies) != 1 || lNumCopies < 1) { lngMessageBox(m_hWnd,ERROR_NUMCOPIES,GENERAL_ERROR,MB_OK | MB_ICONERROR); return false; } // Remember the configuration. g_BurnImageSettings.m_bOnFly = IsDlgButtonChecked(IDC_ONFLYCHECK) == TRUE; g_BurnImageSettings.m_bVerify = IsDlgButtonChecked(IDC_VERIFYCHECK) == TRUE; g_BurnImageSettings.m_bEject = IsDlgButtonChecked(IDC_EJECTCHECK) == TRUE; g_BurnImageSettings.m_bSimulate = IsDlgButtonChecked(IDC_SIMULATECHECK) == TRUE; g_BurnImageSettings.m_bBUP = IsDlgButtonChecked(IDC_BUPCHECK) == TRUE; g_BurnImageSettings.m_bPadTracks = IsDlgButtonChecked(IDC_PADCHECK) == TRUE; g_BurnImageSettings.m_bFixate = IsDlgButtonChecked(IDC_FIXATECHECK) == TRUE; // For internal use only. g_BurnImageSettings.m_pRecorder = reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); g_BurnImageSettings.m_iWriteSpeed = static_cast(m_WriteSpeedCombo.GetItemData(m_WriteSpeedCombo.GetCurSel())); TCHAR szBuffer[32]; GetDlgItemText(IDC_WRITEMETHODCOMBO,szBuffer,32); if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_SAO))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_SAO; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_TAO))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_TAO; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_TAONOPREGAP))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_TAONOPREGAP; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_RAW96R))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_RAW96R; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_RAW16))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_RAW16; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_RAW96P))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_RAW96P; g_BurnImageSettings.m_lNumCopies = lNumCopies; return true; } void CBurnImageGeneralPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/burn_options.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CBurnImageGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_RecorderCombo = GetDlgItem(IDC_RECORDERCOMBO); m_WriteSpeedCombo = GetDlgItem(IDC_WRITESPEEDCOMBO); m_WriteMethodCombo = GetDlgItem(IDC_WRITEMETHODCOMBO); m_NumCopiesCombo = GetDlgItem(IDC_NUMCOPIESCOMBO); // Set the refresh button icon. InitRefreshButton(); // Create the icon. HINSTANCE hInstance = LoadLibrary(_T("shell32.dll")); m_hIcon = (HICON)LoadImage(hInstance,MAKEINTRESOURCE(12),IMAGE_ICON,GetSystemMetrics(SM_CXICON),GetSystemMetrics(SM_CYICON),LR_DEFAULTCOLOR); FreeLibrary(hInstance); SendMessage(GetDlgItem(IDC_ICONSTATIC),STM_SETICON,(WPARAM)m_hIcon,0L); // Recorder combo box. std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; if (!pDevice->recorder()) continue; m_RecorderCombo.AddString(NDeviceUtil::GetDeviceName(*pDevice).c_str()); m_RecorderCombo.SetItemData(m_RecorderCombo.GetCount() - 1, reinterpret_cast(pDevice)); } if (m_RecorderCombo.GetCount() == 0) { m_RecorderCombo.AddString(lngGetString(FAILURE_NORECORDERS)); m_RecorderCombo.EnableWindow(false); m_RecorderCombo.SetCurSel(0); m_WriteSpeedCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_WriteSpeedCombo.EnableWindow(false); m_WriteSpeedCombo.SetCurSel(0); m_WriteMethodCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_WriteMethodCombo.EnableWindow(false); m_WriteMethodCombo.SetCurSel(0); // Disable the OK button. ::EnableWindow(::GetDlgItem(GetParent(),IDOK),false); } else { m_RecorderCombo.SetCurSel(0); if (m_bImageHasTOC) { // Display information message. if (g_GlobalSettings.m_bRawImageInfo) { CInfoDlg InfoDlg(&g_GlobalSettings.m_bRawImageInfo,lngGetString(INFO_RAWIMAGE),INFODLG_NOCANCEL); InfoDlg.DoModal(); } } BOOL bDummy; OnRecorderChange(NULL,NULL,NULL,bDummy); } // Setup the default settings. CheckDlgButton(IDC_ONFLYCHECK,g_BurnImageSettings.m_bOnFly); CheckDlgButton(IDC_VERIFYCHECK,g_BurnImageSettings.m_bVerify); CheckDlgButton(IDC_EJECTCHECK,g_BurnImageSettings.m_bEject); CheckDlgButton(IDC_SIMULATECHECK,g_BurnImageSettings.m_bSimulate); CheckDlgButton(IDC_BUPCHECK,g_BurnImageSettings.m_bBUP); CheckDlgButton(IDC_PADCHECK,g_BurnImageSettings.m_bPadTracks); CheckDlgButton(IDC_FIXATECHECK,g_BurnImageSettings.m_bFixate); // Translate the window. Translate(); // Disable the on the fly check box if requested. if (!m_bEnableOnFly) ::EnableWindow(GetDlgItem(IDC_ONFLYCHECK),FALSE); if (!m_bEnableVerify) ::EnableWindow(GetDlgItem(IDC_VERIFYCHECK),FALSE); // Fill number of copies combo box. TCHAR szBuffer[64]; for (int i = 1; i <= 10; i++) { lsprintf(szBuffer,_T("%d"),i); m_NumCopiesCombo.AddString(szBuffer); } m_NumCopiesCombo.SetCurSel(0); return TRUE; } LRESULT CBurnImageGeneralPage::OnTimer(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { ckmmc::Device *pDevice = reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); // Check for media change. if (g_Core2.CheckMediaChange(*pDevice)) CheckRecorderMedia(); return TRUE; } LRESULT CBurnImageGeneralPage::OnRecorderChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { ckmmc::Device *pDevice = reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); ::SendMessage(GetParent(),WM_SETDEVICE,0,reinterpret_cast(pDevice)); // Kill any already running timers. ::KillTimer(m_hWnd,TIMER_ID); ::SetTimer(m_hWnd,TIMER_ID,TIMER_INTERVAL,NULL); // Initialize the drive media. CheckRecorderMedia(); // General. ::EnableWindow(GetDlgItem(IDC_BUPCHECK),pDevice->support(ckmmc::Device::ckDEVICE_BUP)); bHandled = false; return 0; } LRESULT CBurnImageGeneralPage::OnRefresh(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Initialize the drive media. CheckRecorderMedia(); return 0; } LRESULT CBurnImageGeneralPage::OnFixateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (!IsDlgButtonChecked(IDC_FIXATECHECK)) { // Display warning message. if (g_GlobalSettings.m_bFixateWarning) { CInfoDlg InfoDlg(&g_GlobalSettings.m_bFixateWarning,lngGetString(WARNING_NOFIXATION),INFODLG_ICONWARNING); if (InfoDlg.DoModal() == IDCANCEL) CheckDlgButton(IDC_FIXATECHECK,true); } } return 0; } ================================================ FILE: src/app/dialog/burn_image_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "core2.hh" class CBurnImageGeneralPage : public CPropertyPageImpl { private: bool m_bImageHasTOC; bool m_bEnableOnFly; bool m_bEnableVerify; unsigned int m_uiParentTitleLen; HICON m_hIcon; HICON m_hRefreshIcon; HIMAGELIST m_hRefreshImageList; CComboBox m_RecorderCombo; CComboBox m_WriteSpeedCombo; CComboBox m_WriteMethodCombo; CComboBox m_NumCopiesCombo; enum { TIMER_ID = 42, TIMER_INTERVAL = 1000 }; bool Translate(); bool InitRecorderMedia(); void SuggestWriteMethod(); void InitRefreshButton(); void CheckRecorderMedia(); public: enum { IDD = IDD_PROPPAGE_BURNIMAGEGENERAL }; CBurnImageGeneralPage(bool bImageHasTOC,bool bEnableOnFly,bool bEnableVerify); ~CBurnImageGeneralPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CBurnImageGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_TIMER,OnTimer) COMMAND_HANDLER(IDC_RECORDERCOMBO,CBN_SELCHANGE,OnRecorderChange) COMMAND_HANDLER(IDC_REFRESHBUTTON,BN_CLICKED,OnRefresh) COMMAND_HANDLER(IDC_FIXATECHECK,BN_CLICKED,OnFixateCheck) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnTimer(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnRecorderChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnRefresh(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFixateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/config_advanced_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "config_advanced_page.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" CConfigAdvancedPage::CConfigAdvancedPage() { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_ADVANCED,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CConfigAdvancedPage::~CConfigAdvancedPage() { } bool CConfigAdvancedPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a config translation section. if (!pLng->EnterSection(_T("config"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_LOGCHECK,szStrValue)) SetDlgItemText(IDC_LOGCHECK,szStrValue); if (pLng->GetValuePtr(IDC_SMOKECHECK,szStrValue)) SetDlgItemText(IDC_SMOKECHECK,szStrValue); if (pLng->GetValuePtr(IDC_FIFOGROUPSTATIC,szStrValue)) SetDlgItemText(IDC_FIFOGROUPSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_FIFOINFOSTATIC,szStrValue)) SetDlgItemText(IDC_FIFOINFOSTATIC,szStrValue); return true; } bool CConfigAdvancedPage::OnApply() { TCHAR szFIFO[4]; GetDlgItemText(IDC_FIFOEDIT,szFIFO,4); int iFIFOSize = _wtoi(szFIFO); if (iFIFOSize < FIFO_MIN || iFIFOSize > FIFO_MAX) { TCHAR szMessage[128]; lsnprintf_s(szMessage,128,lngGetString(ERROR_FIFOSIZE),FIFO_MIN,FIFO_MAX); MessageBox(szMessage,lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return false; } // Remember the configuration. g_GlobalSettings.m_bLog = IsDlgButtonChecked(IDC_LOGCHECK) == TRUE; g_GlobalSettings.m_bSmoke = IsDlgButtonChecked(IDC_SMOKECHECK) == TRUE; g_GlobalSettings.m_iFIFOSize = iFIFOSize; return true; } void CConfigAdvancedPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/configuration.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CConfigAdvancedPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Load configuration. CheckDlgButton(IDC_LOGCHECK,g_GlobalSettings.m_bLog); CheckDlgButton(IDC_SMOKECHECK,g_GlobalSettings.m_bSmoke); ::SendMessage(GetDlgItem(IDC_FIFOEDIT),EM_SETLIMITTEXT,3,0); TCHAR szFIFO[4]; _itow(g_GlobalSettings.m_iFIFOSize,szFIFO,10); SetDlgItemText(IDC_FIFOEDIT,szFIFO); // Translate the window. Translate(); return TRUE; } ================================================ FILE: src/app/dialog/config_advanced_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CConfigAdvancedPage : public CPropertyPageImpl { private: bool Translate(); public: enum { IDD = IDD_PROPPAGE_CONFIGADVANCED }; CConfigAdvancedPage(); ~CConfigAdvancedPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CConfigAdvancedPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/config_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "config_dlg.hh" #include "string_table.hh" #include "lang_util.hh" CConfigDlg::CConfigDlg() : CPropertySheetImpl(lngGetString(TITLE_CONFIGURATION),0,NULL) { m_bCentered = false; m_psh.dwFlags |= PSH_NOAPPLYNOW | PSH_HASHELP | PSH_NOCONTEXTHELP; AddPage(m_GeneralPage); AddPage(m_AdvancedPage); AddPage(m_LanguagePage); #ifndef PORTABLE AddPage(m_ShellExtPage); #endif } CConfigDlg::~CConfigDlg() { } LRESULT CConfigDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } bHandled = FALSE; return 0; } ================================================ FILE: src/app/dialog/config_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "config_general_page.hh" #include "config_advanced_page.hh" #include "config_language_page.hh" #include "config_shell_ext_page.hh" class CConfigDlg : public CPropertySheetImpl { private: bool m_bCentered; CConfigGeneralPage m_GeneralPage; CConfigAdvancedPage m_AdvancedPage; CConfigLanguagePage m_LanguagePage; CConfigShellExtPage m_ShellExtPage; public: CConfigDlg(); ~CConfigDlg(); BEGIN_MSG_MAP(CConfigDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/config_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" #include "registry.hh" #include "config_general_page.hh" CConfigGeneralPage::CConfigGeneralPage() { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_GENERAL,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CConfigGeneralPage::~CConfigGeneralPage() { } /* CConfigGeneralPage::IsFileExtRegistered --------------------------------------- Returns true if InfraRecorder is associated with the specified file extension. */ bool CConfigGeneralPage::IsFileExtRegistered(const TCHAR *szFileExt) { CRegistry Reg; Reg.SetRoot(HKEY_CLASSES_ROOT); if (!Reg.OpenKey(szFileExt,false)) return false; TCHAR szKeyName[64]; if (Reg.ReadString(_T(""),szKeyName,64 * sizeof(TCHAR))) { Reg.CloseKey(); if (lstrcmp(szKeyName,_T(""))) { TCHAR szFullName[256]; lstrcpy(szFullName,szKeyName), lstrcat(szFullName,_T("\\shell\\open\\command")); if (!Reg.OpenKey(szFullName,false)) return false; // Compare the file path of this application instance with the file // path in the standard registry key. TCHAR szFilePath[MAX_PATH]; lstrcpy(szFilePath,_T("\"")); GetModuleFileName(NULL,szFilePath + 1,MAX_PATH - 1); lstrcat(szFilePath,_T("\"")); TCHAR szKeyFilePath[MAX_PATH]; if (!Reg.ReadString(_T(""),szKeyFilePath,MAX_PATH * sizeof(TCHAR)) || lstrncmp(szFilePath,szKeyFilePath,lstrlen(szFilePath))) { Reg.CloseKey(); return false; } Reg.CloseKey(); return true; } } return false; } /* CConfigGeneralPage::RegisterFileExt ----------------------------------- Associates InfraRecorder with the specified file extension. Returns true if successfull, otherwise false. szTypeKeyName may not contain more than 64 characters. */ bool CConfigGeneralPage::RegisterFileExt(const TCHAR *szFileExt,const TCHAR *szTypeKeyName, const TCHAR *szTypeDesc) { CRegistry Reg; Reg.SetRoot(HKEY_CLASSES_ROOT); if (Reg.OpenKey(szFileExt)) { TCHAR szKeyName[64]; bool bCreate = false; if (Reg.ReadString(_T(""),szKeyName,sizeof(szKeyName)) || !lstrcmp(szKeyName,_T(""))) { if (lstrcmp(szKeyName,szTypeKeyName)) bCreate = true; } else { bCreate = true; } // If no key is specified we create our own. //if (!Reg.ReadString(_T(""),szKeyName,sizeof(szKeyName)) || !lstrcmp(szKeyName,_T(""))) if (bCreate) { // Extension key name. if (!Reg.WriteString(_T(""),(TCHAR *)szTypeKeyName,lstrlen(szTypeKeyName) * sizeof(TCHAR))) { Reg.CloseKey(); return false; } Reg.CloseKey(); // Key name description. if (!Reg.OpenKey(szTypeKeyName,true)) return false; if (!Reg.WriteString(_T(""),(TCHAR *)szTypeDesc,lstrlen(szTypeDesc) * sizeof(TCHAR))) { Reg.CloseKey(); return false; } } // Open key name and install shell extension. Reg.CloseKey(); TCHAR szFullName[256]; lstrcpy(szFullName,/*szKeyName*/szTypeKeyName), lstrcat(szFullName,_T("\\shell\\open\\command")); if (!Reg.OpenKey(szFullName)) return false; TCHAR szCommand[MAX_PATH]; lstrcpy(szCommand,_T("\"")); GetModuleFileName(NULL,szCommand + 1,MAX_PATH - 1); lstrcat(szCommand,_T("\" %1")); if (!Reg.WriteString(_T(""),szCommand,MAX_PATH * sizeof(TCHAR))) { Reg.CloseKey(); return false; } Reg.CloseKey(); // Set default icon. lstrcpy(szFullName,szKeyName), lstrcat(szFullName,_T("\\DefaultIcon")); if (!Reg.OpenKey(szFullName)) return false; TCHAR szIconPath[MAX_PATH + 2]; GetModuleFileName(NULL,szIconPath,MAX_PATH - 1); lstrcat(szIconPath,_T(",5")); if (!Reg.WriteString(_T(""),szIconPath,MAX_PATH + 2 * sizeof(TCHAR))) { Reg.CloseKey(); return false; } Reg.CloseKey(); return true; } return false; } /* CConfigGeneralPage::UnregisterFileExt ------------------------------------- Deassociate InfraRecorder with the specified file extension. Returns true if the process was successfull, false otherwise. */ bool CConfigGeneralPage::UnregisterFileExt(const TCHAR *szFileExt) { CRegistry Reg; Reg.SetRoot(HKEY_CLASSES_ROOT); if (!Reg.OpenKey(szFileExt,false)) return true; TCHAR szKeyName[64]; if (Reg.ReadString(_T(""),szKeyName,64 * sizeof(TCHAR))) { Reg.CloseKey(); if (lstrcmp(szKeyName,_T(""))) { TCHAR szFullName[256]; lstrcpy(szFullName,szKeyName), lstrcat(szFullName,_T("\\shell\\open")); if (!Reg.OpenKey(szFullName,false)) return false; // Delete the command key. if (!Reg.DeleteKey(_T("command"))) { Reg.CloseKey(); return false; } Reg.CloseKey(); // Delete the open key. szFullName[LastDelimiter(szFullName,'\\')] = '\0'; if (!Reg.OpenKey(szFullName,false)) return false; if (!Reg.DeleteKey(_T("open"))) { Reg.CloseKey(); return false; } // Remove the icon. if (!Reg.OpenKey(szKeyName,false)) return false; bool bResult = Reg.DeleteKey(_T("DefaultIcon")); Reg.CloseKey(); return bResult; } } return true; } bool CConfigGeneralPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a config translation section. if (!pLng->EnterSection(_T("config"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_AUTORUNCHECK,szStrValue)) SetDlgItemText(IDC_AUTORUNCHECK,szStrValue); if (pLng->GetValuePtr(IDC_WIZARDCHECK,szStrValue)) SetDlgItemText(IDC_WIZARDCHECK,szStrValue); if (pLng->GetValuePtr(IDC_ASSOCIATECHECK,szStrValue)) SetDlgItemText(IDC_ASSOCIATECHECK,szStrValue); if (pLng->GetValuePtr(IDC_ASSOCIATEDISCIMAGECHECK,szStrValue)) SetDlgItemText(IDC_ASSOCIATEDISCIMAGECHECK,szStrValue); if (pLng->GetValuePtr(IDC_SHELLFOLDERGROUPSTATIC,szStrValue)) SetDlgItemText(IDC_SHELLFOLDERGROUPSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_SHELLFOLDERINFOSTATIC,szStrValue)) SetDlgItemText(IDC_SHELLFOLDERINFOSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_REMEMBERSHELLCHECK,szStrValue)) SetDlgItemText(IDC_REMEMBERSHELLCHECK,szStrValue); if (pLng->GetValuePtr(IDC_TEMPFOLDERGROUPSTATIC,szStrValue)) SetDlgItemText(IDC_TEMPFOLDERGROUPSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_TEMPFOLDERINFOSTATIC,szStrValue)) SetDlgItemText(IDC_TEMPFOLDERINFOSTATIC,szStrValue); return true; } bool CConfigGeneralPage::OnApply() { // Remember the configuration. g_GlobalSettings.m_bAutoRunCheck = IsDlgButtonChecked(IDC_AUTORUNCHECK) == TRUE; g_GlobalSettings.m_bShowWizard = IsDlgButtonChecked(IDC_WIZARDCHECK) == TRUE; g_GlobalSettings.m_bRememberShell = IsDlgButtonChecked(IDC_REMEMBERSHELLCHECK) == TRUE; GetDlgItemText(IDC_SHELLFOLDEREDIT,g_DynamicSettings.m_szShellDir,MAX_PATH - 1); GetDlgItemText(IDC_TEMPFOLDEREDIT,g_GlobalSettings.m_szTempPath,MAX_PATH - 1); IncludeTrailingBackslash(g_GlobalSettings.m_szTempPath); // Register the project file extension. if (IsDlgButtonChecked(IDC_ASSOCIATECHECK) == TRUE) { RegisterFileExt(_T(".irp"),_T("irproject"),_T("InfraRecorder project")); } else { if (IsFileExtRegistered(_T(".irp"))) UnregisterFileExt(_T(".irp")); } // Register the disc image extensions. if (IsDlgButtonChecked(IDC_ASSOCIATEDISCIMAGECHECK) == TRUE) { RegisterFileExt(_T(".iso"),_T("irdiscimage"),_T("InfraRecorder disc image")); RegisterFileExt(_T(".img"),_T("irdiscimage"),_T("InfraRecorder disc image")); RegisterFileExt(_T(".cue"),_T("irdiscimage"),_T("InfraRecorder disc image")); } else { if (IsFileExtRegistered(_T(".iso"))) UnregisterFileExt(_T(".iso")); if (IsFileExtRegistered(_T(".img"))) UnregisterFileExt(_T(".img")); if (IsFileExtRegistered(_T(".cue"))) UnregisterFileExt(_T(".cue")); } return true; } void CConfigGeneralPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/configuration.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CConfigGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Load configuration. CheckDlgButton(IDC_AUTORUNCHECK,g_GlobalSettings.m_bAutoRunCheck); CheckDlgButton(IDC_WIZARDCHECK,g_GlobalSettings.m_bShowWizard); CheckDlgButton(IDC_REMEMBERSHELLCHECK,g_GlobalSettings.m_bRememberShell); ::SendMessage(GetDlgItem(IDC_SHELLFOLDEREDIT),EM_SETLIMITTEXT,MAX_PATH - 1,0); SetDlgItemText(IDC_SHELLFOLDEREDIT,g_DynamicSettings.m_szShellDir); CheckDlgButton(IDC_ASSOCIATECHECK,IsFileExtRegistered(_T(".irp"))); CheckDlgButton(IDC_ASSOCIATEDISCIMAGECHECK,IsFileExtRegistered(_T(".iso")) || IsFileExtRegistered(_T(".img")) || IsFileExtRegistered(_T(".cue"))); if (g_GlobalSettings.m_bRememberShell) { ::EnableWindow(GetDlgItem(IDC_SHELLFOLDEREDIT),false); ::EnableWindow(GetDlgItem(IDC_SHELLFOLDERBROWSEBUTTON),false); } ::SendMessage(GetDlgItem(IDC_TEMPFOLDEREDIT),EM_SETLIMITTEXT,MAX_PATH - 1,0); SetDlgItemText(IDC_TEMPFOLDEREDIT,g_GlobalSettings.m_szTempPath); // Translate the window. Translate(); return TRUE; } LRESULT CConfigGeneralPage::OnRememberShellCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { bool bEnable = !IsDlgButtonChecked(IDC_REMEMBERSHELLCHECK) == TRUE; ::EnableWindow(GetDlgItem(IDC_SHELLFOLDEREDIT),bEnable); ::EnableWindow(GetDlgItem(IDC_SHELLFOLDERBROWSEBUTTON),bEnable); bHandled = false; return 0; } LRESULT CConfigGeneralPage::OnFolderBrowse(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CFolderDialog FolderDialog(m_hWnd,lngGetString(MISC_SPECIFYFOLDER),BIF_NEWDIALOGSTYLE | BIF_RETURNONLYFSDIRS); int iControlID; switch (wID) { case IDC_SHELLFOLDERBROWSEBUTTON: iControlID = IDC_SHELLFOLDEREDIT; break; case IDC_TEMPFOLDERBROWSEBUTTON: iControlID = IDC_TEMPFOLDEREDIT; break; default: { bHandled = false; return 0; } } if (FolderDialog.DoModal() == IDOK) SetDlgItemText(iControlID,FolderDialog.GetFolderPath()); bHandled = false; return 0; } ================================================ FILE: src/app/dialog/config_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CConfigGeneralPage : public CPropertyPageImpl { private: bool IsFileExtRegistered(const TCHAR *szFileExt); bool RegisterFileExt(const TCHAR *szFileExt,const TCHAR *szTypeKeyName, const TCHAR *szTypeDesc); bool UnregisterFileExt(const TCHAR *szFileExt); bool Translate(); public: enum { IDD = IDD_PROPPAGE_CONFIGGENERAL }; CConfigGeneralPage(); ~CConfigGeneralPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CBurnImageGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDC_REMEMBERSHELLCHECK,OnRememberShellCheck) COMMAND_ID_HANDLER(IDC_SHELLFOLDERBROWSEBUTTON,OnFolderBrowse) COMMAND_ID_HANDLER(IDC_TEMPFOLDERBROWSEBUTTON,OnFolderBrowse) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnRememberShellCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFolderBrowse(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/config_language_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "config_language_page.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" CConfigLanguagePage::CConfigLanguagePage() { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_LANGUAGE,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CConfigLanguagePage::~CConfigLanguagePage() { // Clear the file list vector. m_LangFileList.clear(); } bool CConfigLanguagePage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a config translation section. if (!pLng->EnterSection(_T("config"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_LANGUAGESTATIC,szStrValue)) SetDlgItemText(IDC_LANGUAGESTATIC,szStrValue); if (pLng->GetValuePtr(IDC_LANGUAGEINFOSTATIC,szStrValue)) SetDlgItemText(IDC_LANGUAGEINFOSTATIC,szStrValue); return true; } bool CConfigLanguagePage::OnApply() { // Remember the configuration. int iLangIndex = m_LangCombo.GetCurSel(); if (iLangIndex == 0) g_LanguageSettings.m_szLanguageFile[0] = '\0'; else lstrcpy(g_LanguageSettings.m_szLanguageFile,m_LangFileList[iLangIndex - 1].szFileName); return true; } void CConfigLanguagePage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/configuration.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } ckcore::tstring CConfigLanguagePage::GetTranslationDisplayName(TCHAR *szFileName) { bool bNeedParenthesis = false; ckcore::tstring DispName; size_t iFileNameLen = lstrlen(szFileName); for (size_t i = 0; i < iFileNameLen; i++) { if (i == 0) { DispName.push_back((wchar_t)toupper(szFileName[i])); continue; } if (szFileName[i] == '-') { DispName += TEXT(" ("); bNeedParenthesis = true; continue; } DispName.push_back(szFileName[i]); } if (bNeedParenthesis) DispName.push_back(')'); return DispName; } void CConfigLanguagePage::FillLangCombo() { // Always add the english language item. m_LangCombo.AddString(_T("English (default)")); m_LangCombo.SetCurSel(0); // Add file translations. WIN32_FIND_DATA FileData; HANDLE hFile; // Setup paths. TCHAR szFolderPath[MAX_PATH]; ::GetModuleFileName(NULL,szFolderPath,MAX_PATH - 1); ExtractFilePath(szFolderPath); lstrcat(szFolderPath,_T("languages\\")); TCHAR szFilePath[MAX_PATH]; lstrcpy(szFilePath,szFolderPath); lstrcat(szFilePath,_T("*.irl")); // Get the handle of the first file. hFile = FindFirstFile(szFilePath,&FileData); // Clear the file list vector. m_LangFileList.clear(); if (hFile != INVALID_HANDLE_VALUE) { do { // We want to ingore the "." and ".." records. if (!lstrcmp(FileData.cFileName,TEXT(".")) || !lstrcmp(FileData.cFileName,TEXT(".."))) continue; // Add the file data to the vector. tLangFileData LangFileData; lstrcpy(LangFileData.szFileName,FileData.cFileName); m_LangFileList.push_back(LangFileData); // Remove the file extension and add the item. lstrcpy(szFilePath,FileData.cFileName); ChangeFileExt(szFilePath,_T("")); ckcore::tstring DispName = GetTranslationDisplayName(szFilePath); m_LangCombo.AddString(DispName.c_str()); // Loading the translation name from file is too slow. /*lstrcpy(szFilePath,szFolderPath); lstrcat(szFilePath,FileData.cFileName); CLngProcessor LangFile(szFilePath); if (LangFile.Load() != LNGRES_OK) continue; if (!LangFile.EnterSection(TEXT("translation"))) continue; TCHAR szLangName[256]; if (!LangFile.GetValue(0x0000,szLangName,sizeof(szLangName)/sizeof(TCHAR))) continue; m_LangCombo.AddString(szLangName);*/ if (!lstrcmp(FileData.cFileName,g_LanguageSettings.m_szLanguageFile)) m_LangCombo.SetCurSel(m_LangCombo.GetCount() - 1); } while (FindNextFile(hFile,&FileData)); FindClose(hFile); } } LRESULT CConfigLanguagePage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Setup language combo box. m_LangCombo = GetDlgItem(IDC_LANGUAGECOMBO); // Load configuration. FillLangCombo(); // Translate the window. Translate(); return TRUE; } ================================================ FILE: src/app/dialog/config_language_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "resource.h" typedef struct { TCHAR szFileName[MAX_PATH]; } tLangFileData; class CConfigLanguagePage : public CPropertyPageImpl { private: CComboBox m_LangCombo; std::vector m_LangFileList; bool Translate(); ckcore::tstring GetTranslationDisplayName(TCHAR *szFileName); void FillLangCombo(); public: enum { IDD = IDD_PROPPAGE_CONFIGLANGUAGE }; CConfigLanguagePage(); ~CConfigLanguagePage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CConfigAdvancedPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/config_shell_ext_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "config_shell_ext_page.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "version.hh" #include "new_file_ext_dlg.hh" #include "shell_ext_util.hh" CConfigShellExtPage::CConfigShellExtPage() { m_hToolBarImageList = NULL; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_SHELLEXT,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CConfigShellExtPage::~CConfigShellExtPage() { if (m_hToolBarImageList) ImageList_Destroy(m_hToolBarImageList); } bool CConfigShellExtPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a config translation section. if (!pLng->EnterSection(_T("config"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_SHELLEXTCHECK,szStrValue)) SetDlgItemText(IDC_SHELLEXTCHECK,szStrValue); if (pLng->GetValuePtr(IDC_SHELLEXTSUBMENUCHECK,szStrValue)) SetDlgItemText(IDC_SHELLEXTSUBMENUCHECK,szStrValue); if (pLng->GetValuePtr(IDC_SHELLEXTICONCHECK,szStrValue)) SetDlgItemText(IDC_SHELLEXTICONCHECK,szStrValue); if (pLng->GetValuePtr(IDC_SHELLEXTTEXTSTATIC,szStrValue)) SetDlgItemText(IDC_SHELLEXTTEXTSTATIC,szStrValue); return true; } bool CConfigShellExtPage::OnApply() { // Remember the configuration. g_GlobalSettings.m_bShellExtSubMenu = IsDlgButtonChecked(IDC_SHELLEXTSUBMENUCHECK) == TRUE; g_GlobalSettings.m_bShellExtIcon = IsDlgButtonChecked(IDC_SHELLEXTICONCHECK) == TRUE; if (IsDlgButtonChecked(IDC_SHELLEXTCHECK)) RegisterShellExtension(); else UnregisterShellExtension(); // Associate the individual file extensions. RegisterListView(); return true; } void CConfigShellExtPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/configuration.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } void CConfigShellExtPage::InitToolBarImageList() { // Create the image list. HBITMAP hBitmap; // Get color depth (minimum requirement is 32-bits for alpha blended images). int iBitsPixel = GetDeviceCaps(::GetDC(HWND_DESKTOP),BITSPIXEL); if (g_WinVer.m_ulMajorCCVersion >= 6 && iBitsPixel >= 32) { hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MINITOOLBARBITMAP)); m_hToolBarImageList = ImageList_Create(16,16,ILC_COLOR32,0,6); ImageList_Add(m_hToolBarImageList,hBitmap,NULL); } else { hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MINITOOLBARBITMAP_)); m_hToolBarImageList = ImageList_Create(16,16,ILC_COLOR32 | ILC_MASK,0,6); ImageList_AddMasked(m_hToolBarImageList,hBitmap,RGB(255,0,255)); } DeleteObject(hBitmap); } void CConfigShellExtPage::AddToolBarButton(int iCommand,int iBitmap) { TBBUTTON tbButton; tbButton.fsState = TBSTATE_ENABLED; tbButton.fsStyle = TBSTYLE_BUTTON; tbButton.iBitmap = iBitmap; tbButton.idCommand = iCommand; tbButton.iString = 0; tbButton.dwData = 0; m_ToolBar.InsertButton(m_ToolBar.GetButtonCount(),&tbButton); } void CConfigShellExtPage::CreateToolBarCtrl() { RECT rcListView; m_ListView.GetWindowRect(&rcListView); ScreenToClient(&rcListView); RECT rcToolBar = { 0,0,100,100 }; m_ToolBar.Create(m_hWnd,rcToolBar,NULL,ATL_SIMPLE_TOOLBAR_PANE_STYLE,NULL); m_ToolBar.SetImageList(m_hToolBarImageList); m_ToolBar.SetButtonStructSize(); // Create the buttons. AddToolBarButton(ID_SHELLEXT_ADD,1); AddToolBarButton(ID_SHELLEXT_REMOVE,3); m_ToolBar.EnableButton(ID_SHELLEXT_REMOVE,false); // Disabled by default. // Update the toolbar position. int iToolBarWidth = 0; RECT rcButton; for (int i = 0; i < m_ToolBar.GetButtonCount(); i++) { m_ToolBar.GetItemRect(i,&rcButton); iToolBarWidth += rcButton.right - rcButton.left; } m_ToolBar.SetWindowPos(NULL, rcListView.right - iToolBarWidth, rcListView.top - HIWORD(m_ToolBar.GetButtonSize()), iToolBarWidth, HIWORD(m_ToolBar.GetButtonSize()),0); } void CConfigShellExtPage::CheckListView() { int iDelimiter,iLength; TCHAR *szString; TCHAR *szExt; // Open registry. CRegistry Reg; Reg.SetRoot(HKEY_CLASSES_ROOT); int iItemIndex = -1; iItemIndex = m_ListView.GetNextItem(iItemIndex,LVNI_ALL); while (iItemIndex != -1) { szString = (TCHAR *)m_ListView.GetItemData(iItemIndex); iDelimiter = FirstDelimiter(szString,'|'); szExt = szString + iDelimiter + 1; // Parse the extension list. iLength = lstrlen(szExt); iDelimiter = 0; bool bCheck = true; for (int i = 0; i < iLength; i++) { if (szExt[i] == ',') { // Skip empty extensions. if (iDelimiter == i) { iDelimiter++; continue; } szExt[i] = '\0'; //MessageBox(szExt + iDelimiter); bCheck = bCheck && IsExtensionInstalled(szExt + iDelimiter,&Reg); szExt[i] = ','; iDelimiter = i + 1; // Automatically left trim the (next) string. while (i + 1 < iLength && szExt[i + 1] == ' ') { iDelimiter++; i++; } } } //MessageBox(szExt + iDelimiter); bCheck = bCheck && IsExtensionInstalled(szExt + iDelimiter,&Reg); m_ListView.SetCheckState(iItemIndex,bCheck); iItemIndex = m_ListView.GetNextItem(iItemIndex,LVNI_ALL); } } /* CConfigShellExtPage::RegisterListItem ------------------------------------- Registers or unregisters the list view item with the specified item index. */ void CConfigShellExtPage::RegisterListItem(CRegistry *pReg,int iItemIndex) { TCHAR *szString = (TCHAR *)m_ListView.GetItemData(iItemIndex); int iDelimiter = FirstDelimiter(szString,'|'); TCHAR *szExt = szString + iDelimiter + 1; // Parse the extension list. int iLength = lstrlen(szExt); iDelimiter = 0; bool bRegister = m_ListView.GetCheckState(iItemIndex) == TRUE; for (int i = 0; i < iLength; i++) { if (szExt[i] == ',') { // Skip empty extensions. if (iDelimiter == i) { iDelimiter++; continue; } szExt[i] = '\0'; // Register or unregister the file extension. if (bRegister) { // We separate project files from disc images since they need // another desciption. if (!lstrcmp(szExt,_T(".irp"))) InstallProjectExtension(pReg); else InstallExtension(szExt + iDelimiter,pReg); } else UninstallExtension(szExt + iDelimiter,pReg); szExt[i] = ','; iDelimiter = i + 1; // Automatically left trim the (next) string. while (i + 1 < iLength && szExt[i + 1] == ' ') { iDelimiter++; i++; } } } // Register or unregister the file extension. if (bRegister) { // We separate project files from disc images since they need another desciption. if (!lstrcmp(szExt,_T(".irp"))) InstallProjectExtension(pReg); else InstallExtension(szExt + iDelimiter,pReg); } else UninstallExtension(szExt + iDelimiter,pReg); } /* CConfigShellExtPage::RegisterListView ------------------------------------- Registers and unregisters all extensions found in the list view depending on the item check state. */ void CConfigShellExtPage::RegisterListView() { // Open registry. CRegistry Reg; Reg.SetRoot(HKEY_CLASSES_ROOT); int iItemIndex = -1; iItemIndex = m_ListView.GetNextItem(iItemIndex,LVNI_ALL); while (iItemIndex != -1) { // Register or unregister the item. RegisterListItem(&Reg,iItemIndex); iItemIndex = m_ListView.GetNextItem(iItemIndex,LVNI_ALL); } } LRESULT CConfigShellExtPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Initialize the list view. m_ListView = GetDlgItem(IDC_SHELLEXTLIST); m_ListView.SetExtendedListViewStyle(LVS_EX_FULLROWSELECT | LVS_EX_CHECKBOXES); m_ListView.InsertColumn(0,lngGetString(COLUMN_DESCRIPTION),LVCFMT_LEFT,196,0); m_ListView.InsertColumn(1,lngGetString(COLUMN_EXTENSIONS),LVCFMT_LEFT,150,0); // Fill the list view. int iItemCount = 0; std::list::iterator itNodeObject; for (itNodeObject = g_GlobalSettings.m_szShellExt.begin(); itNodeObject != g_GlobalSettings.m_szShellExt.end(); itNodeObject++) { tstring apa = (*itNodeObject); m_ListView.AddItem(iItemCount,0,LPSTR_TEXTCALLBACK); m_ListView.AddItem(iItemCount,1,LPSTR_TEXTCALLBACK); m_ListView.SetItemData(iItemCount,(DWORD_PTR)(*itNodeObject).c_str()); iItemCount++; } // Check the list view items. CheckListView(); // Tool bar. InitToolBarImageList(); CreateToolBarCtrl(); // Load configuration. CheckDlgButton(IDC_SHELLEXTCHECK,IsShellExtensionRegistered()); CheckDlgButton(IDC_SHELLEXTSUBMENUCHECK,g_GlobalSettings.m_bShellExtSubMenu); CheckDlgButton(IDC_SHELLEXTICONCHECK,g_GlobalSettings.m_bShellExtIcon); // Translate the window. Translate(); return TRUE; } LRESULT CConfigShellExtPage::OnListAdd(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CNewFileExtDlg NewFileExtDlg; if (NewFileExtDlg.DoModal() == IDOK) { TCHAR szBuffer[128]; lstrcpy(szBuffer,NewFileExtDlg.m_szDescBuffer); lstrcat(szBuffer,_T("|")); lstrcat(szBuffer,NewFileExtDlg.m_szExtBuffer); g_GlobalSettings.m_szShellExt.push_back(szBuffer); // Add the list item. int iItemCount = m_ListView.GetItemCount(); m_ListView.AddItem(iItemCount,0,LPSTR_TEXTCALLBACK); m_ListView.AddItem(iItemCount,1,LPSTR_TEXTCALLBACK); m_ListView.SetItemData(iItemCount,(DWORD_PTR)(*--g_GlobalSettings.m_szShellExt.end()).c_str()); } bHandled = false; return 0; } LRESULT CConfigShellExtPage::OnListRemove(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { int iSelItem = m_ListView.GetSelectedIndex(); if (m_ListView.GetCheckState(iSelItem)) { m_ListView.SetCheckState(iSelItem,false); // Unregister the item extensions. CRegistry Reg; Reg.SetRoot(HKEY_CLASSES_ROOT); RegisterListItem(&Reg,iSelItem); } // Remove the list view item. const TCHAR *szString = (const TCHAR *)m_ListView.GetItemData(iSelItem); m_ListView.DeleteItem(m_ListView.GetSelectedIndex()); // Locate and remove the data from the global settings. std::list::iterator itNodeObject; for (itNodeObject = g_GlobalSettings.m_szShellExt.begin(); itNodeObject != g_GlobalSettings.m_szShellExt.end(); itNodeObject++) { if (szString == (*itNodeObject).c_str()) { g_GlobalSettings.m_szShellExt.erase(itNodeObject); break; } } bHandled = false; return 0; } LRESULT CConfigShellExtPage::OnToolBarGetInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { bHandled = true; // The string ID is the same as the button ID. LPTOOLTIPTEXT pTipText = (LPTOOLTIPTEXT)pNMH; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a hint translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("hint"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr((unsigned long)pTipText->hdr.idFrom,szStrValue)) { pTipText->lpszText = szStrValue; return 0; } } } pTipText->lpszText = MAKEINTRESOURCE(pTipText->hdr.idFrom); return 0; } LRESULT CConfigShellExtPage::OnListItemChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { if (m_ToolBar.IsWindow()) { if (m_ListView.GetSelectedCount() > 0) m_ToolBar.EnableButton(ID_SHELLEXT_REMOVE,true); else m_ToolBar.EnableButton(ID_SHELLEXT_REMOVE,false); } bHandled = false; return 0; } LRESULT CConfigShellExtPage::OnListGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { NMLVDISPINFO *pDispInfo = (NMLVDISPINFO *)pNMH; const TCHAR *szString = (const TCHAR *)pDispInfo->item.lParam; if (pDispInfo->item.mask & LVIF_TEXT) { int iDelimiter = FirstDelimiter(szString,'|'); switch (pDispInfo->item.iSubItem) { case 0: { TCHAR *pDelimiter = (TCHAR *)szString + iDelimiter; *pDelimiter = '\0'; lstrcpy(pDispInfo->item.pszText,szString); *pDelimiter = '|'; } break; case 1: { lstrcpy(pDispInfo->item.pszText,(TCHAR *)szString + iDelimiter + 1); } break; } } bHandled = false; return 0; } ================================================ FILE: src/app/dialog/config_shell_ext_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "registry.hh" class CConfigShellExtPage : public CPropertyPageImpl { private: HIMAGELIST m_hToolBarImageList; CListViewCtrl m_ListView; CToolBarCtrl m_ToolBar; bool Translate(); void InitToolBarImageList(); void AddToolBarButton(int iCommand,int iBitmap); void CreateToolBarCtrl(); void CheckListView(); void RegisterListItem(CRegistry *pReg,int iItemIndex); void RegisterListView(); public: enum { IDD = IDD_PROPPAGE_CONFIGSHELLEXT }; CConfigShellExtPage(); ~CConfigShellExtPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CConfigShellExtPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(ID_SHELLEXT_ADD,OnListAdd) COMMAND_ID_HANDLER(ID_SHELLEXT_REMOVE,OnListRemove) NOTIFY_CODE_HANDLER(TTN_GETDISPINFO,OnToolBarGetInfo) NOTIFY_HANDLER(IDC_SHELLEXTLIST,LVN_ITEMCHANGED,OnListItemChanged) NOTIFY_HANDLER(IDC_SHELLEXTLIST,LVN_GETDISPINFO,OnListGetDispInfo) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnListAdd(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnListRemove(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnToolBarGetInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnListItemChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnListGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/confirm_file_replace_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "confirm_file_replace_dlg.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "main_frm.hh" CConfirmFileReplaceDlg::CConfirmFileReplaceDlg() { m_Mode = MODE_ASK; m_szNewFullPath = NULL; m_pNewItemData = NULL; m_pOldItemData = NULL; } CConfirmFileReplaceDlg::~CConfirmFileReplaceDlg() { } bool CConfirmFileReplaceDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is an erase translation section. if (!pLng->EnterSection(_T("confirmfilereplace"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDD_CONFIRMFILEREPLACEDLG,szStrValue)) // Title. SetWindowText(szStrValue); if (pLng->GetValuePtr(IDC_YESBUTTON,szStrValue)) SetDlgItemText(IDC_YESBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_YESALLBUTTON,szStrValue)) SetDlgItemText(IDC_YESALLBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_NOBUTTON,szStrValue)) SetDlgItemText(IDC_NOBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_NOALLBUTTON,szStrValue)) SetDlgItemText(IDC_NOALLBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_INFOSTATIC,szStrValue)) SetDlgItemText(IDC_INFOSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_REPLACEINFOSTATIC,szStrValue)) SetDlgItemText(IDC_REPLACEINFOSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_REPLACEINFO2STATIC,szStrValue)) SetDlgItemText(IDC_REPLACEINFO2STATIC,szStrValue); return true; } /* CConfirmFileReplaceDlg::Reset ----------------------------- Resets the dialog box causing the next call to Execute to display the dialog. */ void CConfirmFileReplaceDlg::Reset() { m_Mode = MODE_ASK; } bool CConfirmFileReplaceDlg::Execute() { bool bResult = false; switch (DoModal(*g_pMainFrame)) // It's okay if g_pMainFrame->m_hWnd is NULL. { case IDC_YESBUTTON: bResult = true; break; case IDC_YESALLBUTTON: m_Mode = MODE_YESALL; bResult = true; break; case IDC_NOBUTTON: break; case IDC_NOALLBUTTON: m_Mode = MODE_NOALL; break; }; return bResult; } /* CConfirmFileReplaceDlg::Execute ------------------------------- Returns true if the file is selected to be replaced and false if it isn't. This function will determine if it's necessary to display the dialog at all. The user might have pressed the "No to All" or "Yes to All" buttons. */ bool CConfirmFileReplaceDlg::Execute(const TCHAR *szNewFullPath,CItemData *pOldItemData) { // Should we ask the user? if (m_Mode != MODE_ASK) return m_Mode == MODE_YESALL ? true : false; m_szNewFullPath = szNewFullPath; m_pNewItemData = NULL; m_pOldItemData = pOldItemData; return Execute(); } bool CConfirmFileReplaceDlg::Execute(CItemData *pNewItemData,CItemData *pOldItemData) { // Should we ask the user? if (m_Mode != MODE_ASK) return m_Mode == MODE_YESALL ? true : false; m_szNewFullPath = NULL; m_pNewItemData = pNewItemData; m_pOldItemData = pOldItemData; return Execute(); } LRESULT CConfirmFileReplaceDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); // Make sure that all necessary data has been supplied. if ((m_szNewFullPath == NULL && m_pNewItemData == NULL) || m_pOldItemData == NULL) return TRUE; // Set the copy icon. ::SendMessage(GetDlgItem(IDC_ICONSTATIC),STM_SETICON, (WPARAM)LoadIcon(LoadLibrary(_T("shell32.dll")),MAKEINTRESOURCE(146)),0L); // Translate the window. Translate(); // File name. TCHAR szNewFileText[128]; ::GetWindowText(GetDlgItem(IDC_INFOSTATIC),szNewFileText, sizeof(szNewFileText) - 2 - lstrlen(m_pOldItemData->GetFileName())); lstrcat(szNewFileText,_T("\n")); lstrcat(szNewFileText,m_pOldItemData->GetFileName()); ::SetWindowText(GetDlgItem(IDC_INFOSTATIC),szNewFileText); // Set old icon. SHFILEINFO shInfo; if (SHGetFileInfo(m_pOldItemData->szFullPath,0,&shInfo,sizeof(shInfo), SHGFI_ICON | SHGFI_USEFILEATTRIBUTES)) { ::SendMessage(GetDlgItem(IDC_OLDICONSTATIC),STM_SETICON,(WPARAM)shInfo.hIcon,0L); } // Set old size. TCHAR szTempBuffer[128]; FormatBytes(szTempBuffer,m_pOldItemData->uiSize); ::SetWindowText(GetDlgItem(IDC_OLDSIZESTATIC),szTempBuffer); // Set old date. FILETIME ft; SYSTEMTIME st; TCHAR *szDatePattern = new TCHAR[lstrlen(lngGetString(MISC_MODIFIED)) + 24]; lstrcpy(szDatePattern,_T("'")); lstrcat(szDatePattern,lngGetString(MISC_MODIFIED)); lstrcat(szDatePattern,_T(" 'dddd',' dd MMMM yyyy")); ::DosDateTimeToFileTime(m_pOldItemData->usFileDate,m_pOldItemData->usFileTime,&ft); ::FileTimeToSystemTime(&ft,&st); ::GetDateFormat(LOCALE_USER_DEFAULT,0,&st,szDatePattern,szTempBuffer,sizeof(szTempBuffer)); ::SetWindowText(GetDlgItem(IDC_OLDDATESTATIC),szTempBuffer); if (m_szNewFullPath != NULL) { // Set new icon. if (SHGetFileInfo(m_szNewFullPath,0,&shInfo,sizeof(shInfo), SHGFI_ICON | SHGFI_USEFILEATTRIBUTES)) { ::SendMessage(GetDlgItem(IDC_NEWICONSTATIC),STM_SETICON,(WPARAM)shInfo.hIcon,0L); } // Set new size. FormatBytes(szTempBuffer,ckcore::File::size(m_szNewFullPath)); ::SetWindowText(GetDlgItem(IDC_NEWSIZESTATIC),szTempBuffer); // Set new date. unsigned short usFileDate = 0,usFileTime = 0; struct tm AccessTime,ModifyTime,CreateTime; ckcore::File::time(m_szNewFullPath,AccessTime,ModifyTime,CreateTime); ckcore::convert::tm_to_dostime(ModifyTime,usFileDate,usFileTime); ::DosDateTimeToFileTime(usFileDate,usFileTime,&ft); ::FileTimeToSystemTime(&ft,&st); ::GetDateFormat(LOCALE_USER_DEFAULT,0,&st,szDatePattern,szTempBuffer,sizeof(szTempBuffer)); ::SetWindowText(GetDlgItem(IDC_NEWDATESTATIC),szTempBuffer); } else { // Set new icon. if (SHGetFileInfo(m_pNewItemData->szFullPath,0,&shInfo,sizeof(shInfo), SHGFI_ICON | SHGFI_USEFILEATTRIBUTES)) { ::SendMessage(GetDlgItem(IDC_NEWICONSTATIC),STM_SETICON,(WPARAM)shInfo.hIcon,0L); } // Set new size. FormatBytes(szTempBuffer,m_pNewItemData->uiSize); ::SetWindowText(GetDlgItem(IDC_NEWSIZESTATIC),szTempBuffer); // Set new date. ::DosDateTimeToFileTime(m_pNewItemData->usFileDate,m_pNewItemData->usFileTime,&ft); ::FileTimeToSystemTime(&ft,&st); ::GetDateFormat(LOCALE_USER_DEFAULT,0,&st,szDatePattern,szTempBuffer,sizeof(szTempBuffer)); ::SetWindowText(GetDlgItem(IDC_NEWDATESTATIC),szTempBuffer); } delete [] szDatePattern; return TRUE; } LRESULT CConfirmFileReplaceDlg::OnButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } ================================================ FILE: src/app/dialog/confirm_file_replace_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "tree_manager.hh" class CConfirmFileReplaceDlg : public CDialogImpl { private: enum eMode { MODE_ASK, MODE_YESALL, MODE_NOALL }; eMode m_Mode; const TCHAR *m_szNewFullPath; CItemData *m_pNewItemData; CItemData *m_pOldItemData; bool Translate(); bool Execute(); public: enum { IDD = IDD_CONFIRMFILEREPLACEDLG }; CConfirmFileReplaceDlg(); ~CConfirmFileReplaceDlg(); void Reset(); bool Execute(const TCHAR *szNewFullPath,CItemData *pOldItemData); bool Execute(CItemData *pNewItemData,CItemData *pOldItemData); BEGIN_MSG_MAP(CConfirmFileReplaceDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDC_YESBUTTON,OnButton) COMMAND_ID_HANDLER(IDC_YESALLBUTTON,OnButton) COMMAND_ID_HANDLER(IDC_NOBUTTON,OnButton) COMMAND_ID_HANDLER(IDC_NOALLBUTTON,OnButton) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/copy_disc_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "string_table.hh" #include "lang_util.hh" #include "copy_disc_dlg.hh" CCopyDiscDlg::CCopyDiscDlg(bool bAppMode) : m_bCentered(false),m_bAppMode(bAppMode), m_pSrcDevice(NULL),m_pDstDevice(NULL), CPropertySheetImpl(lngGetString(COPYDISC_TITLE),0,NULL), m_GeneralPage(), m_ReadPage(false,false) { m_psh.dwFlags |= PSH_NOAPPLYNOW | PSH_HASHELP | PSH_NOCONTEXTHELP; AddPage(m_GeneralPage); AddPage(m_AdvancedPage); AddPage(m_ReadPage); } CCopyDiscDlg::~CCopyDiscDlg() { } LRESULT CCopyDiscDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } // Add the dialog to the task bar and enable it to be minimized. if (m_bAppMode) { ModifyStyle(0,WS_MINIMIZEBOX | WS_SYSMENU); ModifyStyleEx(0,WS_EX_APPWINDOW); HMENU hSysMenu = GetSystemMenu(FALSE); ::InsertMenu(hSysMenu,0,MF_BYPOSITION,SC_RESTORE,_T("&Restore")); ::InsertMenu(hSysMenu,2,MF_BYPOSITION,SC_MINIMIZE,_T("Mi&nimize")); ::InsertMenu(hSysMenu,3,MF_BYPOSITION | MF_SEPARATOR,0,_T("")); } bHandled = FALSE; return 0; } LRESULT CCopyDiscDlg::OnSetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (wParam == 1) m_pSrcDevice = reinterpret_cast(lParam); else m_pDstDevice = reinterpret_cast(lParam); bHandled = TRUE; return 0; } LRESULT CCopyDiscDlg::OnGetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { bHandled = TRUE; return reinterpret_cast(wParam == 1 ? m_pSrcDevice : m_pDstDevice); } LRESULT CCopyDiscDlg::OnSetCloneMode(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_ReadPage.SetCloneMode(wParam == TRUE); bHandled = TRUE; return 0; } ================================================ FILE: src/app/dialog/copy_disc_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "copy_disc_general_page.hh" #include "burn_advanced_page.hh" #include "read_options_page.hh" #include "ctrl_messages.hh" class CCopyDiscDlg : public CPropertySheetImpl { private: bool m_bCentered; bool m_bAppMode; ckmmc::Device *m_pSrcDevice; ckmmc::Device *m_pDstDevice; CCopyDiscGeneralPage m_GeneralPage; CBurnAdvancedPage m_AdvancedPage; CReadOptionsPage m_ReadPage; public: CCopyDiscDlg(bool bAppMode); ~CCopyDiscDlg(); BEGIN_MSG_MAP(CCopyDiscDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) MESSAGE_HANDLER(WM_SETDEVICE,OnSetDevice) MESSAGE_HANDLER(WM_GETDEVICE,OnGetDevice) MESSAGE_HANDLER(WM_SETCLONEMODE,OnSetCloneMode) CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnGetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSetCloneMode(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/copy_disc_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "infrarecorder.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" #include "ctrl_messages.hh" #include "cdrtools_parse_strings.hh" #include "wait_dlg.hh" #include "scsi.hh" #include "trans_util.hh" #include "device_util.hh" #include "core2_util.hh" #include "version.hh" #include "visual_styles.hh" #include "info_dlg.hh" #include "copy_disc_general_page.hh" CCopyDiscGeneralPage::CCopyDiscGeneralPage() { m_uiParentTitleLen = 0; m_hRefreshIcon = NULL; m_hRefreshImageList = NULL; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_GENERAL,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; // Specify which controls that are located beloe the burn on the fly warning // label. m_iCtrlsBelowOnFly.push_back(IDC_CLONECHECK); m_iCtrlsBelowOnFly.push_back(IDC_BEVELSTATIC5); m_iCtrlsBelowOnFly.push_back(IDC_WRITESPEEDSTATIC); m_iCtrlsBelowOnFly.push_back(IDC_WRITESPEEDCOMBO); m_iCtrlsBelowOnFly.push_back(IDC_WRITEMETHODSTATIC); m_iCtrlsBelowOnFly.push_back(IDC_WRITEMETHODCOMBO); m_iCtrlsBelowOnFly.push_back(IDC_BEVELSTATIC4); m_iCtrlsBelowOnFly.push_back(IDC_EJECTCHECK); m_iCtrlsBelowOnFly.push_back(IDC_SIMULATECHECK); m_iCtrlsBelowOnFly.push_back(IDC_BUPCHECK); m_iCtrlsBelowOnFly.push_back(IDC_PADCHECK); m_iCtrlsBelowOnFly.push_back(IDC_FIXATECHECK); } CCopyDiscGeneralPage::~CCopyDiscGeneralPage() { if (m_hRefreshImageList != NULL) ImageList_Destroy(m_hRefreshImageList); if (m_hRefreshIcon != NULL) DestroyIcon(m_hRefreshIcon); } bool CCopyDiscGeneralPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a burn translation section. if (!pLng->EnterSection(_T("burn"))) return false; // Translate. TCHAR *szStrValue; int iMaxStaticRight = 0; if (pLng->GetValuePtr(IDC_WRITESPEEDSTATIC,szStrValue)) { SetDlgItemText(IDC_WRITESPEEDSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_WRITESPEEDSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_WRITEMETHODSTATIC,szStrValue)) { SetDlgItemText(IDC_WRITEMETHODSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_WRITEMETHODSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_EJECTCHECK,szStrValue)) SetDlgItemText(IDC_EJECTCHECK,szStrValue); if (pLng->GetValuePtr(IDC_SIMULATECHECK,szStrValue)) SetDlgItemText(IDC_SIMULATECHECK,szStrValue); if (pLng->GetValuePtr(IDC_BUPCHECK,szStrValue)) SetDlgItemText(IDC_BUPCHECK,szStrValue); if (pLng->GetValuePtr(IDC_PADCHECK,szStrValue)) SetDlgItemText(IDC_PADCHECK,szStrValue); if (pLng->GetValuePtr(IDC_FIXATECHECK,szStrValue)) SetDlgItemText(IDC_FIXATECHECK,szStrValue); // Make sure that there is a copy translation section. if (!pLng->EnterSection(_T("copy"))) return false; if (pLng->GetValuePtr(IDC_SOURCESTATIC,szStrValue)) SetDlgItemText(IDC_SOURCESTATIC,szStrValue); if (pLng->GetValuePtr(IDC_TARGETSTATIC,szStrValue)) SetDlgItemText(IDC_TARGETSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_ONFLYCHECK,szStrValue)) SetDlgItemText(IDC_ONFLYCHECK,szStrValue); if (pLng->GetValuePtr(IDC_ONFLYSTATIC,szStrValue)) { SetDlgItemText(IDC_ONFLYSTATIC,szStrValue); int iDiff = UpdateStaticHeight(m_hWnd,IDC_ONFLYSTATIC,szStrValue); if (iDiff > 0) { for (unsigned int i = 0; i < m_iCtrlsBelowOnFly.size(); i++) { RECT rcControl = { 0 }; ::GetWindowRect(GetDlgItem(m_iCtrlsBelowOnFly[i]),&rcControl); ScreenToClient(&rcControl); ::MoveWindow(GetDlgItem(m_iCtrlsBelowOnFly[i]),rcControl.left, rcControl.top + iDiff,rcControl.right - rcControl.left, rcControl.bottom - rcControl.top,TRUE); } /*RECT rcWindow = { 0 }; GetWindowRect(&rcWindow); MoveWindow(rcWindow.left, rcWindow.top,rcWindow.right - rcWindow.left, rcWindow.bottom - rcWindow.top + iDiff,TRUE);*/ } } if (pLng->GetValuePtr(IDC_CLONECHECK,szStrValue)) SetDlgItemText(IDC_CLONECHECK,szStrValue); // Make sure that the edit controls are not in the way of the statics. if (iMaxStaticRight > 75) { UpdateEditPos(m_hWnd,IDC_WRITESPEEDCOMBO,iMaxStaticRight,true); UpdateEditPos(m_hWnd,IDC_WRITEMETHODCOMBO,iMaxStaticRight,true); } return true; } bool CCopyDiscGeneralPage::InitRecorderMedia() { if (m_uiParentTitleLen == 0) m_uiParentTitleLen = GetParentWindow(this).GetWindowTextLength(); TCHAR szBuffer[256]; GetParentWindow(this).GetWindowText(szBuffer,m_uiParentTitleLen + 1); ckmmc::Device &Device = *reinterpret_cast(m_TargetCombo.GetItemData( m_TargetCombo.GetCurSel())); Device.refresh(); // Get current profile. ckmmc::Device::Profile Profile = Device.profile(); // Note: On CD-R/RW media the Test Write bit is valid only for Write Type // 1 or 2 (Track at Once or Session at Once). On DVD-R media, the Test // Write bit is valid only for Write Type 0 or 2 (Incremental or // Disc-at-once). This is completely disregarded at the moment. bool bSupportedProfile = false; switch (Profile) { case ckmmc::Device::ckPROFILE_DVDRAM: case ckmmc::Device::ckPROFILE_DVDPLUSRW: case ckmmc::Device::ckPROFILE_DVDPLUSRW_DL: case ckmmc::Device::ckPROFILE_DVDMINUSRW_RESTOV: case ckmmc::Device::ckPROFILE_DVDMINUSRW_SEQ: case ckmmc::Device::ckPROFILE_DVDPLUSR: case ckmmc::Device::ckPROFILE_DVDPLUSR_DL: // Not sure about these: case ckmmc::Device::ckPROFILE_BDROM: case ckmmc::Device::ckPROFILE_BDR_SRM: case ckmmc::Device::ckPROFILE_BDR_RRM: case ckmmc::Device::ckPROFILE_BDRE: case ckmmc::Device::ckPROFILE_HDDVDROM: case ckmmc::Device::ckPROFILE_HDDVDR: case ckmmc::Device::ckPROFILE_HDDVDRAM: bSupportedProfile = true; // Disable simulation (not supported for DVD+RW media). ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK),FALSE); break; case ckmmc::Device::ckPROFILE_CDR: case ckmmc::Device::ckPROFILE_CDRW: case ckmmc::Device::ckPROFILE_DVDMINUSR_SEQ: case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_SEQ: case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_JUMP: bSupportedProfile = true; // Enable simulation if supported by recorder. ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK), Device.support(ckmmc::Device::ckDEVICE_TEST_WRITE)); break; case ckmmc::Device::ckPROFILE_NONE: lstrcat(szBuffer,_T(" ")); lstrcat(szBuffer,lngGetString(MEDIA_INSERTBLANK)); break; default: lstrcat(szBuffer,_T(" ")); lstrcat(szBuffer,lngGetString(MEDIA_UNSUPPORTED)); break; } GetParentWindow(this).SetWindowText(szBuffer); if (bSupportedProfile) { // Maximum write speed. m_WriteSpeedCombo.ResetContent(); m_WriteSpeedCombo.AddString(lngGetString(MISC_MAXIMUM)); m_WriteSpeedCombo.SetItemData(0,static_cast(-1)); m_WriteSpeedCombo.SetCurSel(0); // Other supported write speeds. const std::vector &WriteSpeeds = Device.write_speeds(); std::vector::const_iterator it; for (it = WriteSpeeds.begin(); it != WriteSpeeds.end(); it++) { m_WriteSpeedCombo.AddString(ckmmc::util::kb_to_disp_speed(*it,Profile).c_str()); m_WriteSpeedCombo.SetItemData(m_WriteSpeedCombo.GetCount() - 1, static_cast(ckmmc::util::kb_to_human_speed(*it, /*ckmmc::Device::ckPROFILE_CDR*/Profile))); } // Write modes. m_WriteMethodCombo.ResetContent(); if (Device.support(ckmmc::Device::ckWM_SAO)) m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_SAO)); if (Device.support(ckmmc::Device::ckWM_TAO)) { m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_TAO)); m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_TAONOPREGAP)); } if (Device.support(ckmmc::Device::ckWM_RAW96R)) m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_RAW96R)); if (Device.support(ckmmc::Device::ckWM_RAW16)) m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_RAW16)); if (Device.support(ckmmc::Device::ckWM_RAW96P)) m_WriteMethodCombo.AddString(lngGetString(WRITEMODE_RAW96P)); m_WriteMethodCombo.SetCurSel(0); } else { return false; } return true; } void CCopyDiscGeneralPage::InitRefreshButton() { m_hRefreshIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_REFRESHICON),IMAGE_ICON,/*GetSystemMetrics(SM_CXICON)*/16,/*GetSystemMetrics(SM_CYICON)*/16,LR_DEFAULTCOLOR); // In Windows XP there is a bug causing the button to loose it's themed style if // assigned an icon. The solution to this is to assign an image list instead. if (g_WinVer.m_ulMajorCCVersion >= 6) { // Get color depth (minimum requirement is 32-bits for alpha blended images). int iBitsPixel = GetDeviceCaps(::GetDC(HWND_DESKTOP),BITSPIXEL); m_hRefreshImageList = ImageList_Create(16,16,ILC_COLOR32 | (iBitsPixel < 32 ? ILC_MASK : 0),0,1); ImageList_AddIcon(m_hRefreshImageList,m_hRefreshIcon); BUTTON_IMAGELIST bImageList; bImageList.himl = m_hRefreshImageList; bImageList.margin.left = 0; bImageList.margin.top = 0; bImageList.margin.right = 0; bImageList.margin.bottom = 0; bImageList.uAlign = BUTTON_IMAGELIST_ALIGN_CENTER; SendMessage(GetDlgItem(IDC_REFRESHBUTTON),BCM_SETIMAGELIST,0,(LPARAM)&bImageList); } else { SendMessage(GetDlgItem(IDC_REFRESHBUTTON),BM_SETIMAGE,IMAGE_ICON,(LPARAM)m_hRefreshIcon); } // If the application is themed, then adjust the size of the button. if (g_VisualStyles.IsThemeActive()) { RECT rcButton; ::GetWindowRect(GetDlgItem(IDC_REFRESHBUTTON),&rcButton); ScreenToClient(&rcButton); ::SetWindowPos(GetDlgItem(IDC_REFRESHBUTTON),NULL,rcButton.left - 1,rcButton.top - 1, rcButton.right - rcButton.left + 2,rcButton.bottom - rcButton.top + 2,0); } } void CCopyDiscGeneralPage::CheckRecorderMedia() { bool bMediaInit = InitRecorderMedia(); if (!bMediaInit) { // Write speed. m_WriteSpeedCombo.ResetContent(); m_WriteSpeedCombo.AddString(lngGetString(MISC_MAXIMUM)); m_WriteSpeedCombo.SetCurSel(0); // Write method. m_WriteMethodCombo.ResetContent(); m_WriteMethodCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_WriteMethodCombo.SetCurSel(0); } m_WriteSpeedCombo.EnableWindow(bMediaInit); m_WriteMethodCombo.EnableWindow(bMediaInit); ::EnableWindow(::GetDlgItem(GetParent(),IDOK),bMediaInit); ::EnableWindow(GetDlgItem(IDC_WRITESPEEDSTATIC),bMediaInit); ::EnableWindow(GetDlgItem(IDC_WRITEMETHODSTATIC),bMediaInit); } bool CCopyDiscGeneralPage::OnApply() { // Remember the configuration. g_CopyDiscSettings.m_bOnFly = IsDlgButtonChecked(IDC_ONFLYCHECK) == TRUE; g_CopyDiscSettings.m_bClone = IsDlgButtonChecked(IDC_CLONECHECK) == TRUE; g_BurnImageSettings.m_bEject = IsDlgButtonChecked(IDC_EJECTCHECK) == TRUE; g_BurnImageSettings.m_bSimulate = IsDlgButtonChecked(IDC_SIMULATECHECK) == TRUE; g_BurnImageSettings.m_bBUP = IsDlgButtonChecked(IDC_BUPCHECK) == TRUE; g_BurnImageSettings.m_bPadTracks = IsDlgButtonChecked(IDC_PADCHECK) == TRUE; g_BurnImageSettings.m_bFixate = IsDlgButtonChecked(IDC_FIXATECHECK) == TRUE; ckmmc::Device *pSrcDevice = reinterpret_cast(m_SourceCombo.GetItemData( m_SourceCombo.GetCurSel())); if (g_CopyDiscSettings.m_bOnFly && !AnalyzeDriveMedia(*pSrcDevice)) { MessageBox(_T("Unable to get source drive media information. Can not continue."),lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return false; } // For internal use only. g_CopyDiscSettings.m_pSource = reinterpret_cast(m_SourceCombo.GetItemData( m_SourceCombo.GetCurSel())); g_CopyDiscSettings.m_pTarget = reinterpret_cast(m_TargetCombo.GetItemData( m_TargetCombo.GetCurSel())); g_BurnImageSettings.m_iWriteSpeed = static_cast(m_WriteSpeedCombo.GetItemData(m_WriteSpeedCombo.GetCurSel())); TCHAR szBuffer[32]; GetDlgItemText(IDC_WRITEMETHODCOMBO,szBuffer,32); if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_SAO))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_SAO; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_TAO))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_TAO; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_TAONOPREGAP))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_TAONOPREGAP; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_RAW96R))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_RAW96R; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_RAW16))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_RAW16; else if (!lstrcmp(szBuffer,lngGetString(WRITEMODE_RAW96P))) g_BurnImageSettings.m_iWriteMethod = WRITEMETHOD_RAW96P; g_BurnImageSettings.m_lNumCopies = 1; return true; } void CCopyDiscGeneralPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/copy_data_disc.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CCopyDiscGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_SourceCombo = GetDlgItem(IDC_SOURCECOMBO); m_TargetCombo = GetDlgItem(IDC_TARGETCOMBO); m_WriteSpeedCombo = GetDlgItem(IDC_WRITESPEEDCOMBO); m_WriteMethodCombo = GetDlgItem(IDC_WRITEMETHODCOMBO); // Set the refresh button icon. InitRefreshButton(); // Source combo box. std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; m_SourceCombo.AddString(NDeviceUtil::GetDeviceName(*pDevice).c_str()); m_SourceCombo.SetItemData(m_SourceCombo.GetCount() - 1, reinterpret_cast(pDevice)); } if (m_SourceCombo.GetCount() == 0) { m_SourceCombo.AddString(lngGetString(FAILURE_NODEVICES)); m_SourceCombo.EnableWindow(false); } m_SourceCombo.SetCurSel(0); // Target combo box. for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; // We only want to add recorder to the list. if (!pDevice->recorder()) continue; m_TargetCombo.AddString(NDeviceUtil::GetDeviceName(*pDevice).c_str()); m_TargetCombo.SetItemData(m_TargetCombo.GetCount() - 1, reinterpret_cast(pDevice)); } if (m_TargetCombo.GetCount() == 0) { m_TargetCombo.AddString(lngGetString(FAILURE_NORECORDERS)); m_TargetCombo.EnableWindow(false); m_TargetCombo.SetCurSel(0); m_WriteSpeedCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_WriteSpeedCombo.EnableWindow(false); m_WriteSpeedCombo.SetCurSel(0); m_WriteMethodCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_WriteMethodCombo.EnableWindow(false); m_WriteMethodCombo.SetCurSel(0); // Disable the OK button. ::EnableWindow(::GetDlgItem(GetParent(),IDOK),false); } else { m_TargetCombo.SetCurSel(0); BOOL bDummy; OnTargetChange(NULL,NULL,NULL,bDummy); } // Setup the default settings. CheckDlgButton(IDC_ONFLYCHECK,g_CopyDiscSettings.m_bOnFly); CheckDlgButton(IDC_CLONECHECK,g_CopyDiscSettings.m_bClone); ::SendMessage(GetParent(),WM_SETCLONEMODE,g_CopyDiscSettings.m_bClone,0); CheckDlgButton(IDC_EJECTCHECK,g_BurnImageSettings.m_bEject); CheckDlgButton(IDC_SIMULATECHECK,g_BurnImageSettings.m_bSimulate); CheckDlgButton(IDC_BUPCHECK,g_BurnImageSettings.m_bBUP); CheckDlgButton(IDC_PADCHECK,g_BurnImageSettings.m_bPadTracks); CheckDlgButton(IDC_FIXATECHECK,g_BurnImageSettings.m_bFixate); BOOL bDummy; OnFlyCheck(NULL,NULL,NULL,bDummy); if (::IsWindowEnabled(::GetDlgItem(GetParent(),IDOK))) OnCloneCheck(NULL,NULL,NULL,bDummy); // Make sure that the same device is not selected as both target and source. OnSourceChange(NULL,NULL,NULL,bDummy); // Translate the window. Translate(); return TRUE; } LRESULT CCopyDiscGeneralPage::OnTimer(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { ckmmc::Device *pDstDevice = reinterpret_cast(m_TargetCombo.GetItemData( m_TargetCombo.GetCurSel())); // Check for media change. if (g_Core2.CheckMediaChange(*pDstDevice)) CheckRecorderMedia(); return TRUE; } unsigned long CCopyDiscGeneralPage::MSFToLBA(unsigned long ulMin,unsigned long ulSec, unsigned long ulFrame) { return ((ulMin * 60 * 75) + (ulSec * 75) + ulFrame - 150); } bool CCopyDiscGeneralPage::AnalyzeDriveMedia(ckmmc::Device &Device) { // Rescan the bus. CWaitDlg WaitDlg; WaitDlg.Create(m_hWnd); WaitDlg.ShowWindow(SW_SHOW); // Initialize device (detect drive letter, open handle, count tracks). WaitDlg.SetMessage(lngGetString(INIT_DEVICECD)); TCHAR szDriveLetter[3]; szDriveLetter[0] = Device.address().device_[0]; szDriveLetter[1] = ':'; szDriveLetter[2] = '\0'; // Get the allocated space on the source drive. ULARGE_INTEGER uiAvailable; ULARGE_INTEGER uiTotal; ULARGE_INTEGER uiFree; uiAvailable.QuadPart = 0; uiTotal.QuadPart = 0; uiFree.QuadPart = 0; if (GetDiskFreeSpaceEx(szDriveLetter,&uiAvailable,&uiTotal,&uiFree)) g_CopyDiscSettings.m_uiSourceSize = uiTotal.QuadPart; WaitDlg.DestroyWindow(); return true; } LRESULT CCopyDiscGeneralPage::OnSourceChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { ckmmc::Device *pSrcDevice = reinterpret_cast(m_SourceCombo.GetItemData( m_SourceCombo.GetCurSel())); ckmmc::Device *pDstDevice = reinterpret_cast(m_TargetCombo.GetItemData( m_TargetCombo.GetCurSel())); ::SendMessage(GetParent(),WM_SETDEVICE,1,reinterpret_cast(pSrcDevice)); // Disable/enable the record on the fly button. ::EnableWindow(GetDlgItem(IDC_ONFLYCHECK),pSrcDevice != pDstDevice); if (pSrcDevice == pDstDevice) CheckDlgButton(IDC_ONFLYCHECK,false); BOOL bDummy; OnFlyCheck(NULL,NULL,NULL,bDummy); bHandled = false; return 0; } LRESULT CCopyDiscGeneralPage::OnTargetChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // If you insert a CD and immediately open this dialog, the application // will be unresponsive for a few seconds while the device is being opened // [see m_CurDevice.Open() below]. It would be best to avoid that pause // altogether, but at least we display the hourglass cursor here, to let // the user know he should be patient, otherwise he might try to click all // over the place and wonder why nothing happens. CWaitCursor WaitCursor; // This displays the hourglass cursor. ckmmc::Device *pSrcDevice = reinterpret_cast(m_SourceCombo.GetItemData( m_SourceCombo.GetCurSel())); ckmmc::Device *pDstDevice = reinterpret_cast(m_TargetCombo.GetItemData( m_TargetCombo.GetCurSel())); ::SendMessage(GetParent(),WM_SETDEVICE,0,reinterpret_cast(pDstDevice)); // Kill any already running timers. ::KillTimer(m_hWnd,TIMER_ID); ::SetTimer(m_hWnd,TIMER_ID,TIMER_INTERVAL,NULL); // Initialize the drive media. CheckRecorderMedia(); // General. ::EnableWindow(GetDlgItem(IDC_BUPCHECK), pDstDevice->support(ckmmc::Device::ckDEVICE_BUP)); // Suggest an appropriate write method if necessary. BOOL bDummy; if (IsDlgButtonChecked(IDC_ONFLYCHECK) == FALSE) OnCloneCheck(0,0,NULL,bDummy); else m_WriteMethodCombo.SetCurSel(0); // Disable/enable the record on the fly button. ::EnableWindow(GetDlgItem(IDC_ONFLYCHECK),pSrcDevice != pDstDevice); if (pSrcDevice == pDstDevice) CheckDlgButton(IDC_ONFLYCHECK,false); OnFlyCheck(NULL,NULL,NULL,bDummy); bHandled = false; return 0; } LRESULT CCopyDiscGeneralPage::OnRefresh(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Initialize the drive media. CheckRecorderMedia(); return 0; } LRESULT CCopyDiscGeneralPage::OnFlyCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Enable/disable the clone disc check box. if (IsDlgButtonChecked(IDC_ONFLYCHECK) == FALSE) { ::EnableWindow(GetDlgItem(IDC_CLONECHECK),TRUE); } else { ::EnableWindow(GetDlgItem(IDC_CLONECHECK),FALSE); // Select the top write method (usually SAO). m_WriteMethodCombo.SetCurSel(0); // Disable and uncheck the clone check box. CheckDlgButton(IDC_CLONECHECK,FALSE); ::SendMessage(GetParent(),WM_SETCLONEMODE,FALSE,0); } bHandled = false; return 0; } LRESULT CCopyDiscGeneralPage::OnCloneCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Try to select a recommended write method. if (IsDlgButtonChecked(IDC_CLONECHECK)) { ::SendMessage(GetParent(),WM_SETCLONEMODE,TRUE,0); ckmmc::Device &DstDevice = *reinterpret_cast(m_TargetCombo.GetItemData( m_TargetCombo.GetCurSel())); // Check for supported write modes. Raw96r has the highest priority, if // that's not support the raw16 mode is recommended, if none of the mentioned // write modes are supported a warning message is displayed. int uiStrID = -1; if (DstDevice.support(ckmmc::Device::ckWM_RAW96R)) uiStrID = WRITEMODE_RAW96R; else if (DstDevice.support(ckmmc::Device::ckWM_RAW16)) uiStrID = WRITEMODE_RAW16; const TCHAR *szStr = lngGetString(uiStrID); if (uiStrID != -1) { TCHAR szItemText[128]; for (int i = 0; i < m_WriteMethodCombo.GetCount(); i++) { if (m_WriteMethodCombo.GetLBTextLen(i) >= (sizeof(szItemText) / sizeof(TCHAR))) continue; m_WriteMethodCombo.GetLBText(i,szItemText); if (!lstrcmp(szItemText,szStr)) { m_WriteMethodCombo.SetCurSel(i); break; } } } else { // No good raw writing mode found. MessageBox(lngGetString(WARNING_CLONEWRITEMETHOD),lngGetString(GENERAL_WARNING), MB_OK | MB_ICONWARNING); } } else { ::SendMessage(GetParent(),WM_SETCLONEMODE,FALSE,0); m_WriteMethodCombo.SetCurSel(0); } bHandled = false; return 0; } LRESULT CCopyDiscGeneralPage::OnFixateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (!IsDlgButtonChecked(IDC_FIXATECHECK)) { // Display warning message. if (g_GlobalSettings.m_bFixateWarning) { CInfoDlg InfoDlg(&g_GlobalSettings.m_bFixateWarning,lngGetString(WARNING_NOFIXATION),INFODLG_ICONWARNING); if (InfoDlg.DoModal() == IDCANCEL) CheckDlgButton(IDC_FIXATECHECK,true); } } return 0; } ================================================ FILE: src/app/dialog/copy_disc_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "resource.h" #include "core2.hh" class CCopyDiscGeneralPage : public CPropertyPageImpl { private: unsigned int m_uiParentTitleLen; HICON m_hRefreshIcon; HIMAGELIST m_hRefreshImageList; CComboBox m_SourceCombo; CComboBox m_TargetCombo; CComboBox m_WriteSpeedCombo; CComboBox m_WriteMethodCombo; // This vectors holds the IDs of all controls located below the burn on the fly // warning label. These controls will be moved to make the translated text fit // if necessary. std::vector m_iCtrlsBelowOnFly; enum { TIMER_ID = 42, TIMER_INTERVAL = 1000 }; bool Translate(); bool InitRecorderMedia(); bool AnalyzeDriveMedia(ckmmc::Device &Device); void InitRefreshButton(); void CheckRecorderMedia(); unsigned long MSFToLBA(unsigned long ulMin,unsigned long ulSec,unsigned long ulFrame); public: enum { IDD = IDD_PROPPAGE_COPYDISCGENERAL }; CCopyDiscGeneralPage(); ~CCopyDiscGeneralPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CCopyDiscGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_TIMER,OnTimer) COMMAND_HANDLER(IDC_SOURCECOMBO,CBN_SELCHANGE,OnSourceChange) COMMAND_HANDLER(IDC_TARGETCOMBO,CBN_SELCHANGE,OnTargetChange) COMMAND_HANDLER(IDC_REFRESHBUTTON,BN_CLICKED,OnRefresh) COMMAND_HANDLER(IDC_FIXATECHECK,BN_CLICKED,OnFixateCheck) COMMAND_ID_HANDLER(IDC_ONFLYCHECK,OnFlyCheck) COMMAND_ID_HANDLER(IDC_CLONECHECK,OnCloneCheck) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnTimer(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSourceChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnTargetChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnRefresh(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFlyCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCloneCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFixateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/copy_image_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "copy_image_dlg.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" #include "wait_dlg.hh" #include "scsi.hh" CCopyImageDlg::CCopyImageDlg(bool bAppMode) : m_bCentered(false),m_bAppMode(bAppMode),m_pSrcDevice(NULL), CPropertySheetImpl(lngGetString(COPYIMAGE_TITLE),0,NULL), m_ReadPage(true,true) { m_psh.dwFlags |= PSH_NOAPPLYNOW | PSH_HASHELP | PSH_NOCONTEXTHELP; AddPage(m_GeneralPage); AddPage(m_ReadPage); } CCopyImageDlg::~CCopyImageDlg() { } LRESULT CCopyImageDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } // Add the dialog to the task bar and enable it to be minimized. if (m_bAppMode) { ModifyStyle(0,WS_MINIMIZEBOX | WS_SYSMENU); ModifyStyleEx(0,WS_EX_APPWINDOW); HMENU hSysMenu = GetSystemMenu(FALSE); ::InsertMenu(hSysMenu,0,MF_BYPOSITION,SC_RESTORE,_T("&Restore")); ::InsertMenu(hSysMenu,2,MF_BYPOSITION,SC_MINIMIZE,_T("Mi&nimize")); ::InsertMenu(hSysMenu,3,MF_BYPOSITION | MF_SEPARATOR,0,_T("")); } bHandled = FALSE; return 0; } LRESULT CCopyImageDlg::OnSetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_pSrcDevice = reinterpret_cast(lParam); bHandled = TRUE; return 0; } LRESULT CCopyImageDlg::OnGetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { bHandled = TRUE; return reinterpret_cast(m_pSrcDevice); } LRESULT CCopyImageDlg::OnCheckMediaBroadcast(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (m_GeneralPage.IsWindow()) ::SendMessage(m_GeneralPage,WM_CHECKMEDIA,wParam,lParam); if (m_ReadPage.IsWindow()) ::SendMessage(m_ReadPage,WM_CHECKMEDIA,wParam,lParam); bHandled = TRUE; return 0; } TCHAR *CCopyImageDlg::GetFileName() { return m_GeneralPage.GetFileName(); } ================================================ FILE: src/app/dialog/copy_image_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "copy_image_general_page.hh" #include "read_options_page.hh" #include "ctrl_messages.hh" class CCopyImageDlg : public CPropertySheetImpl { private: bool m_bCentered; bool m_bAppMode; ckmmc::Device *m_pSrcDevice; CCopyImageGeneralPage m_GeneralPage; CReadOptionsPage m_ReadPage; public: CCopyImageDlg(bool bAppMode); ~CCopyImageDlg(); BEGIN_MSG_MAP(CCopyImageDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) MESSAGE_HANDLER(WM_SETDEVICE,OnSetDevice) MESSAGE_HANDLER(WM_GETDEVICE,OnGetDevice) MESSAGE_HANDLER(WM_CHECKMEDIA_BROADCAST,OnCheckMediaBroadcast) CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnGetDevice(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnCheckMediaBroadcast(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); TCHAR *GetFileName(); }; ================================================ FILE: src/app/dialog/copy_image_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "infrarecorder.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "ctrl_messages.hh" #include "trans_util.hh" #include "version.hh" #include "visual_styles.hh" #include "device_util.hh" #include "copy_image_general_page.hh" CCopyImageGeneralPage::CCopyImageGeneralPage() { m_uiParentTitleLen = 0; m_hRefreshIcon = NULL; m_hRefreshImageList = NULL; m_szFileName[0] = '\0'; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_GENERAL,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CCopyImageGeneralPage::~CCopyImageGeneralPage() { if (m_hRefreshImageList != NULL) ImageList_Destroy(m_hRefreshImageList); if (m_hRefreshIcon != NULL) DestroyIcon(m_hRefreshIcon); } bool CCopyImageGeneralPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a copy translation section. if (!pLng->EnterSection(_T("copy"))) return false; // Translate. TCHAR *szStrValue; int iMaxStaticRight = 0; if (pLng->GetValuePtr(IDC_SOURCESTATIC,szStrValue)) { SetDlgItemText(IDC_SOURCESTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_SOURCESTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_IMAGESTATIC,szStrValue)) { SetDlgItemText(IDC_IMAGESTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_IMAGESTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } // Make sure that the edit/combo controls are not in the way of the statics. if (iMaxStaticRight > 75) { UpdateEditPos(m_hWnd,IDC_SOURCECOMBO,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_IMAGEEDIT,iMaxStaticRight); } return true; } void CCopyImageGeneralPage::InitRefreshButton() { m_hRefreshIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_REFRESHICON),IMAGE_ICON,/*GetSystemMetrics(SM_CXICON)*/16,/*GetSystemMetrics(SM_CYICON)*/16,LR_DEFAULTCOLOR); // In Windows XP there is a bug causing the button to loose it's themed style if // assigned an icon. The solution to this is to assign an image list instead. if (g_WinVer.m_ulMajorCCVersion >= 6) { // Get color depth (minimum requirement is 32-bits for alpha blended images). int iBitsPixel = GetDeviceCaps(::GetDC(HWND_DESKTOP),BITSPIXEL); m_hRefreshImageList = ImageList_Create(16,16,ILC_COLOR32 | (iBitsPixel < 32 ? ILC_MASK : 0),0,1); ImageList_AddIcon(m_hRefreshImageList,m_hRefreshIcon); BUTTON_IMAGELIST bImageList; bImageList.himl = m_hRefreshImageList; bImageList.margin.left = 0; bImageList.margin.top = 0; bImageList.margin.right = 0; bImageList.margin.bottom = 0; bImageList.uAlign = BUTTON_IMAGELIST_ALIGN_CENTER; SendMessage(GetDlgItem(IDC_REFRESHBUTTON),BCM_SETIMAGELIST,0,(LPARAM)&bImageList); } else { SendMessage(GetDlgItem(IDC_REFRESHBUTTON),BM_SETIMAGE,IMAGE_ICON,(LPARAM)m_hRefreshIcon); } // If the application is themed, then adjust the size of the button. if (g_VisualStyles.IsThemeActive()) { RECT rcButton; ::GetWindowRect(GetDlgItem(IDC_REFRESHBUTTON),&rcButton); ScreenToClient(&rcButton); ::SetWindowPos(GetDlgItem(IDC_REFRESHBUTTON),NULL,rcButton.left - 1,rcButton.top - 1, rcButton.right - rcButton.left + 2,rcButton.bottom - rcButton.top + 2,0); } } bool CCopyImageGeneralPage::OnApply() { // For internal use only. g_CopyDiscSettings.m_pSource = reinterpret_cast(m_SourceCombo.GetItemData( m_SourceCombo.GetCurSel())); GetDlgItemText(IDC_IMAGEEDIT,m_szFileName,MAX_PATH - 1); return true; } void CCopyImageGeneralPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/copy_data_disc.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CCopyImageGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_SourceCombo = GetDlgItem(IDC_SOURCECOMBO); // Set the refresh button icon. InitRefreshButton(); // Source combo box. std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; m_SourceCombo.AddString(NDeviceUtil::GetDeviceName(*pDevice).c_str()); m_SourceCombo.SetItemData(m_SourceCombo.GetCount() - 1, reinterpret_cast(pDevice)); } if (m_SourceCombo.GetCount() == 0) { m_SourceCombo.AddString(lngGetString(FAILURE_NODEVICES)); m_SourceCombo.SetItemData(0,0); m_SourceCombo.EnableWindow(false); ::EnableWindow(GetDlgItem(IDC_BROWSEBUTTON),false); } m_SourceCombo.SetCurSel(0); // Disable the OK button. ::EnableWindow(::GetDlgItem(GetParent(),IDOK),false); // Let the parent know which source drive that's selected. BOOL bDummy; OnSourceChange(NULL,NULL,NULL,bDummy); // Translate the window. Translate(); return TRUE; } LRESULT CCopyImageGeneralPage::OnTimer(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { ckmmc::Device *pDevice = reinterpret_cast(m_SourceCombo.GetItemData(m_SourceCombo.GetCurSel())); ATLASSERT(sizeof(ckmmc::Device *) == sizeof(LPARAM)); // Check for media change. if (g_Core2.CheckMediaChange(*pDevice)) { GetParentWindow(this).SendMessage(WM_CHECKMEDIA_BROADCAST,0, reinterpret_cast(pDevice)); } return TRUE; } LRESULT CCopyImageGeneralPage::OnSourceChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { ckmmc::Device *pSrcDevice = reinterpret_cast(m_SourceCombo.GetItemData( m_SourceCombo.GetCurSel())); ::SendMessage(GetParent(),WM_SETDEVICE,1,reinterpret_cast(pSrcDevice)); // Kill any already running timers. ::KillTimer(m_hWnd,TIMER_ID); ::SetTimer(m_hWnd,TIMER_ID,TIMER_INTERVAL,NULL); // Initialize the drive media. GetParentWindow(this).SendMessage(WM_CHECKMEDIA_BROADCAST,0, m_SourceCombo.GetItemData(m_SourceCombo.GetCurSel())); bHandled = false; return 0; } LRESULT CCopyImageGeneralPage::OnRefresh(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Initialize the drive media. GetParentWindow(this).SendMessage(WM_CHECKMEDIA_BROADCAST,0, m_SourceCombo.GetItemData(m_SourceCombo.GetCurSel())); return 0; } LRESULT CCopyImageGeneralPage::OnBrowse(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { WTL::CFileDialog FileDialog(false,_T("iso"),_T("Untitled"),OFN_EXPLORER | OFN_OVERWRITEPROMPT, _T("Disc Images (*.iso)\0*.iso\0\0"),m_hWnd); if (FileDialog.DoModal() == IDOK) { SetDlgItemText(IDC_IMAGEEDIT,FileDialog.m_szFileName); ::EnableWindow(::GetDlgItem(GetParent(),IDOK),true); } return 0; } TCHAR *CCopyImageGeneralPage::GetFileName() { return m_szFileName; } ================================================ FILE: src/app/dialog/copy_image_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "core2.hh" class CCopyImageGeneralPage : public CPropertyPageImpl { private: unsigned int m_uiParentTitleLen; HICON m_hRefreshIcon; HIMAGELIST m_hRefreshImageList; CComboBox m_SourceCombo; // File name of the target image file. TCHAR m_szFileName[MAX_PATH]; enum { TIMER_ID = 42, TIMER_INTERVAL = 1000 }; bool Translate(); void InitRefreshButton(); public: enum { IDD = IDD_PROPPAGE_COPYIMAGEGENERAL }; CCopyImageGeneralPage(); ~CCopyImageGeneralPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CCopyImageGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_TIMER,OnTimer) COMMAND_HANDLER(IDC_SOURCECOMBO,CBN_SELCHANGE,OnSourceChange) COMMAND_HANDLER(IDC_REFRESHBUTTON,BN_CLICKED,OnRefresh) COMMAND_ID_HANDLER(IDC_BROWSEBUTTON,OnBrowse) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnTimer(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSourceChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnRefresh(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnBrowse(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); TCHAR *GetFileName(); }; ================================================ FILE: src/app/dialog/device_advanced_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "string_table.hh" #include "lang_util.hh" #include "settings.hh" #include "cdrtools_parse_strings.hh" #include "device_advanced_page.hh" CDeviceAdvancedPage::CDeviceAdvancedPage(ckmmc::Device &Device) : m_Device(Device) { // If set to true the list view will not accept any item changes, that // includes both selection and checking. m_bLockAdvList = false; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_ADVANCED,szStrValue)) SetTitle(szStrValue); } } } CDeviceAdvancedPage::~CDeviceAdvancedPage() { } bool CDeviceAdvancedPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a device translation section. if (!pLng->EnterSection(_T("device"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_INFOSTATIC,szStrValue)) SetDlgItemText(IDC_INFOSTATIC,szStrValue); return true; } LRESULT CDeviceAdvancedPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Fill the list view. m_ListView.SubclassWindow(GetDlgItem(IDC_ADVLIST)); m_ListView.Initialize(); m_ListView.SetExtendedListViewStyle(LVS_EX_CHECKBOXES); m_ListView.AddColumn(_T(""),0); m_ListView.SetColumnWidth(0,370); // General. unsigned int uiItemCount = 0; m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_MODE2FORM1)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_MODE_2_FORM_1)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_MODE2FORM2)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_MODE_2_FORM_2)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_READDIGAUDIO)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_CDDA_SUPPORTED)); if (m_Device.support(ckmmc::Device::ckDEVICE_CDDA_SUPPORTED)) { m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_RESTARTNSDARA)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_CDDA_ACCURATE)); } m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_READMULTSESSION)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_MULTI_SESSION)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_READFIXPACKET)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_METHOD_2)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_READBARCODE)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_READ_BAR_CODE)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_READRWSUBCODE)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_RW_SUPPORTED)); if (m_Device.support(ckmmc::Device::ckDEVICE_RW_SUPPORTED)) { m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_READRAWPWSC)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_RW_DEINT_CORR)); } m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_SIMULATION)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_TEST_WRITE)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_BUFRECORDING)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_BUP)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_C2EP)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_C2_POINTERS)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_EJECTCDSS)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_EJECT)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_CHANGEDISCSIDE)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_CHANGE_SIDES)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_INDIVIDUALDP)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_CHANGE_DISC_PRSNT)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_RETURNCDCN)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_UPC)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_RETURNCDISRC)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_ISRC)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_DELIVCOMPOSITE)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_COMPOSITE)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_PLAYAUDIOCD)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_AUDIO_PLAY)); if (m_Device.support(ckmmc::Device::ckDEVICE_AUDIO_PLAY)) { m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_INDIVIDUALVC)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_SEP_CHAN_VOL)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_INDEPENDENTMUTE)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_SEP_CHAN_MUTE)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_DOPORT1)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_DIGITAL_PORT_1)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_DOPORT2)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_DIGITAL_PORT_2)); // Digital output. if (m_Device.support(ckmmc::Device::ckDEVICE_DIGITAL_PORT_1) || m_Device.support(ckmmc::Device::ckDEVICE_DIGITAL_PORT_2)) { m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_DOSENDDIGDAT)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_LSBF)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_DOSETLRCK)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_RCK)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_HASVALIDDATA)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_BCKF)); } } m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_HASLESIC)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_SSS)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_LMOPU)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_PREVENT_JUMPER)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_ALLOWML)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckDEVICE_LOCK)); // Write methods. m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_SAO)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckWM_SAO)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_TAO)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckWM_TAO)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_RAW96R)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckWM_RAW96R)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_RAW16)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckWM_RAW16)); m_ListView.AddItem(uiItemCount,0,lngGetString(ADVPROP_RAW96P)); m_ListView.SetCheckState(uiItemCount++,m_Device.support(ckmmc::Device::ckWM_RAW96P)); m_bLockAdvList = true; // Translate the window. Translate(); return TRUE; } LRESULT CDeviceAdvancedPage::OnItemChanging(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { return m_bLockAdvList; } ================================================ FILE: src/app/dialog/device_advanced_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "resource.h" #include "title_tip_list_view_ctrl.hh" class CDeviceAdvancedPage : public CPropertyPageImpl { private: ckmmc::Device &m_Device; bool m_bLockAdvList; CTitleTipListViewCtrl m_ListView; bool Translate(); public: enum { IDD = IDD_PROPPAGE_DEVICEADVANCED }; CDeviceAdvancedPage(ckmmc::Device &Device); ~CDeviceAdvancedPage(); BEGIN_MSG_MAP(CDeviceAdvancedPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) NOTIFY_HANDLER(IDC_ADVLIST,LVN_ITEMCHANGING,OnItemChanging) CHAIN_MSG_MAP(CPropertyPageImpl) CHAIN_MSG_MAP_MEMBER(m_ListView) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnItemChanging(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/device_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "device_dlg.hh" CDeviceDlg::CDeviceDlg(ckmmc::Device &Device,const TCHAR *szTitle) : CPropertySheetImpl(szTitle,0,NULL), m_GeneralPage(Device),m_AdvancedPage(Device) { m_bCentered = false; m_psh.dwFlags |= PSH_NOAPPLYNOW | PSH_NOCONTEXTHELP; AddPage(m_GeneralPage); AddPage(m_AdvancedPage); } CDeviceDlg::~CDeviceDlg() { } LRESULT CDeviceDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } bHandled = FALSE; return 0; } ================================================ FILE: src/app/dialog/device_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "device_general_page.hh" #include "device_advanced_page.hh" class CDeviceDlg : public CPropertySheetImpl { private: bool m_bCentered; CDeviceGeneralPage m_GeneralPage; CDeviceAdvancedPage m_AdvancedPage; public: CDeviceDlg(ckmmc::Device &Device,const TCHAR *szTitle); ~CDeviceDlg(); BEGIN_MSG_MAP(CDeviceDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/device_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "device_util.hh" #include "string_table.hh" #include "lang_util.hh" #include "settings.hh" #include "info_dlg.hh" #include "device_general_page.hh" CDeviceGeneralPage::CDeviceGeneralPage(ckmmc::Device &Device) : m_hIcon(NULL),m_Device(Device) { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_GENERAL,szStrValue)) SetTitle(szStrValue); } } } CDeviceGeneralPage::~CDeviceGeneralPage() { if (m_hIcon != NULL) DestroyIcon(m_hIcon); } bool CDeviceGeneralPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a device translation section. if (!pLng->EnterSection(_T("device"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_TYPELABELSTATIC,szStrValue)) SetDlgItemText(IDC_TYPELABELSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_LOCATIONLABELSTATIC,szStrValue)) SetDlgItemText(IDC_LOCATIONLABELSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_BUFFERLABELSTATIC,szStrValue)) SetDlgItemText(IDC_BUFFERLABELSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_MAXREADLABELSTATIC,szStrValue)) SetDlgItemText(IDC_MAXREADLABELSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_MAXWRITELABELSTATIC,szStrValue)) SetDlgItemText(IDC_MAXWRITELABELSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_READSTATIC,szStrValue)) SetDlgItemText(IDC_READSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_WRITESTATIC,szStrValue)) SetDlgItemText(IDC_WRITESTATIC,szStrValue); return true; } void CDeviceGeneralPage::PrintDeviceType(ckmmc::Device &Device) { if (Device.support(ckmmc::Device::ckDEVICE_WRITE_CDR) || Device.support(ckmmc::Device::ckDEVICE_WRITE_CDRW)) { if (Device.support(ckmmc::Device::ckDEVICE_WRITE_DVDR) || Device.support(ckmmc::Device::ckDEVICE_WRITE_DVDRAM)) { SetDlgItemText(IDC_TYPESTATIC,lngGetString(DEVICETYPE_DVDRECORDER)); } else { SetDlgItemText(IDC_TYPESTATIC,lngGetString(DEVICETYPE_CDRECORDER)); } } else { if (Device.support(ckmmc::Device::ckDEVICE_READ_DVDROM) || Device.support(ckmmc::Device::ckDEVICE_READ_DVDR) || Device.support(ckmmc::Device::ckDEVICE_READ_DVDRAM)) { SetDlgItemText(IDC_TYPESTATIC,lngGetString(DEVICETYPE_DVDREADER)); } else { SetDlgItemText(IDC_TYPESTATIC,lngGetString(DEVICETYPE_CDREADER)); } } } LRESULT CDeviceGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Create the icon. HINSTANCE hInstance = LoadLibrary(_T("shell32.dll")); m_hIcon = (HICON)LoadImage(hInstance,MAKEINTRESOURCE(12),IMAGE_ICON, GetSystemMetrics(SM_CXICON),GetSystemMetrics(SM_CYICON),LR_DEFAULTCOLOR); FreeLibrary(hInstance); SendMessage(GetDlgItem(IDC_ICONSTATIC),STM_SETICON,(WPARAM)m_hIcon,0L); // Display the information. SetDlgItemText(IDC_NAMESTATIC,NDeviceUtil::GetDeviceName(m_Device).c_str()); // Type. PrintDeviceType(m_Device); // Location. TCHAR szBuffer[128]; lsnprintf_s(szBuffer,128,lngGetString(PROPERTIES_DEVICELOC),m_Device.address().bus_, m_Device.address().target_,m_Device.address().lun_); SetDlgItemText(IDC_LOCATIONSTATIC,szBuffer); // Buffer size. lsprintf(szBuffer,_T("%d kB"),m_Device.property(ckmmc::Device::ckPROP_BUFFER_SIZE)); SetDlgItemText(IDC_BUFFERSTATIC,szBuffer); // Max read speed. ckcore::tuint32 max_read_speed = m_Device.property(ckmmc::Device::ckPROP_MAX_READ_SPD); lsprintf(szBuffer,_T("%d sectors/s (CD: %s, DVD: %s)"), max_read_speed, ckmmc::util::kb_to_disp_speed(max_read_speed, ckmmc::Device::ckPROFILE_CDROM).c_str(), ckmmc::util::kb_to_disp_speed(max_read_speed, ckmmc::Device::ckPROFILE_DVDROM).c_str()); SetDlgItemText(IDC_MAXREADSTATIC,szBuffer); // Max write speed. ckcore::tuint32 max_write_speed = m_Device.property(ckmmc::Device::ckPROP_MAX_WRITE_SPD); lsprintf(szBuffer,_T("%d sectors/s (CD: %s, DVD: %s)"), max_write_speed, ckmmc::util::kb_to_disp_speed(max_write_speed, ckmmc::Device::ckPROFILE_CDROM).c_str(), ckmmc::util::kb_to_disp_speed(max_write_speed, ckmmc::Device::ckPROFILE_DVDROM).c_str()); SetDlgItemText(IDC_MAXWRITESTATIC,szBuffer); // Read media. ::SendMessage(GetDlgItem(IDC_READCDRCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_CDR) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READCDRWCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_CDRW) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READDVDRCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_DVDR) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READDVDRAMCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_DVDRAM) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READDVDROMCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_DVDROM) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READDVDPLUSRCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_DVDPLUSR) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READDVDPLUSRWCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_DVDPLUSRW) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READDVDPLUSRDLCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_DVDPLUSR_DL) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READDVDPLUSRWDLCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_DVDPLUSRW_DL) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READBDCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_BD) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_READHDDVDCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_READ_HDDVD) ? BST_INDETERMINATE : BST_UNCHECKED,0); // Write media. ::SendMessage(GetDlgItem(IDC_WRITECDRCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_CDR) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_WRITECDRWCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_CDRW) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_WRITEDVDRCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_DVDR) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_WRITEDVDRAMCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_DVDRAM) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_WRITEDVDPLUSRCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_DVDPLUSR) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_WRITEDVDPLUSRWCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_DVDPLUSRW) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_WRITEDVDPLUSRDLCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_DVDPLUSR_DL) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_WRITEDVDPLUSRWDLCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_DVDPLUSRW_DL) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_WRITEBDCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_BD) ? BST_INDETERMINATE : BST_UNCHECKED,0); ::SendMessage(GetDlgItem(IDC_WRITEHDDVDCHECK),BM_SETCHECK, m_Device.support(ckmmc::Device::ckDEVICE_WRITE_HDDVD) ? BST_INDETERMINATE : BST_UNCHECKED,0); // Translate the window. Translate(); return TRUE; } ================================================ FILE: src/app/dialog/device_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "resource.h" class CDeviceGeneralPage : public CPropertyPageImpl { private: HICON m_hIcon; ckmmc::Device &m_Device; bool Translate(); void PrintDeviceType(ckmmc::Device &Device); public: enum { IDD = IDD_PROPPAGE_DEVICEGENERAL }; CDeviceGeneralPage(ckmmc::Device &Device); ~CDeviceGeneralPage(); BEGIN_MSG_MAP(CDeviceGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnWriteSpeedSpin(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/devices_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "infrarecorder.hh" #include "device_dlg.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" #include "device_util.hh" #include "devices_dlg.hh" void CDevicesDlg::ScanCallback::event_status(ckmmc::DeviceManager::ScanCallback::Status Status) { if (Status == ckmmc::DeviceManager::ScanCallback::ckEVENT_DEV_SCAN) { m_WaitDlg.SetMessage(lngGetString(INIT_SCANBUS)); } else if (Status == ckmmc::DeviceManager::ScanCallback::ckEVENT_DEV_CAP) { m_WaitDlg.SetMessage(lngGetString(INIT_LOADCAPABILITIES)); } } bool CDevicesDlg::ScanCallback::event_device(ckmmc::Device::Address &Addr) { return true; } CDevicesDlg::CDevicesDlg() { m_hListImageList = NULL; } CDevicesDlg::~CDevicesDlg() { if (m_hListImageList) ImageList_Destroy(m_hListImageList); } bool CDevicesDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a devices translation section. if (!pLng->EnterSection(_T("devices"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDD_DEVICESDLG,szStrValue)) // Title. SetWindowText(szStrValue); if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDC_HELPBUTTON,szStrValue)) SetDlgItemText(IDC_HELPBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_RESCANBUTTON,szStrValue)) SetDlgItemText(IDC_RESCANBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_INFOSTATIC,szStrValue)) SetDlgItemText(IDC_INFOSTATIC,szStrValue); return true; } void CDevicesDlg::FillListView() { int iItemCount = 0; std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; TCHAR szBuffer[64]; if (pDevice->address().bus_ == -1 || pDevice->address().target_ == -1 || pDevice->address().lun_ == -1) { m_ListView.AddItem(iItemCount,0,_T("[?,?,?]"),0); } else { lsprintf(szBuffer,_T("[%d,%d,%d]"),pDevice->address().bus_, pDevice->address().target_,pDevice->address().lun_); m_ListView.AddItem(iItemCount,0,szBuffer,0); } lsprintf(szBuffer,_T("%c:"),pDevice->address().device_[0]); m_ListView.AddItem(iItemCount,1,szBuffer,0); m_ListView.AddItem(iItemCount,2,pDevice->vendor(),0); m_ListView.AddItem(iItemCount,3,pDevice->identifier(),0); m_ListView.AddItem(iItemCount,4,pDevice->revision(),0); m_ListView.SetItemData(iItemCount,reinterpret_cast(pDevice)); iItemCount++; } } void CDevicesDlg::InitializeListView() { // Create the image list. HINSTANCE hInstance = LoadLibrary(_T("shell32.dll")); HICON hIcon = (HICON)LoadImage(hInstance,MAKEINTRESOURCE(12),IMAGE_ICON,16,16,/*LR_DEFAULTCOLOR*/LR_LOADTRANSPARENT); FreeLibrary(hInstance); m_hListImageList = ImageList_Create(16,16,ILC_COLOR32,0,1); ImageList_AddIcon(m_hListImageList,hIcon); DestroyIcon(hIcon); // Setup the list view. m_ListView.SubclassWindow(GetDlgItem(IDC_DEVICELIST)); m_ListView.SetImageList(m_hListImageList,LVSIL_NORMAL); m_ListView.SetImageList(m_hListImageList,LVSIL_SMALL); m_ListView.SetExtendedListViewStyle(LVS_EX_FULLROWSELECT); // Add the columns. m_ListView.AddColumn(lngGetString(COLUMN_ID),0); m_ListView.SetColumnWidth(0,60); m_ListView.AddColumn(lngGetString(COLUMN_DRIVE),1); m_ListView.SetColumnWidth(1,40); // 25 is not enough for wide letters like "W:" m_ListView.AddColumn(lngGetString(COLUMN_VENDOR),2); m_ListView.SetColumnWidth(2,65); m_ListView.AddColumn(lngGetString(COLUMN_IDENTIFICATION),3); m_ListView.SetColumnWidth(3,125); m_ListView.AddColumn(lngGetString(COLUMN_REVISION),4); m_ListView.SetColumnWidth(4,55); } LRESULT CDevicesDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); // Initialize the list view. InitializeListView(); // Fill the list view. FillListView(); // Translate the window. Translate(); return TRUE; } LRESULT CDevicesDlg::OnDestroy(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Detach the internal list view control. m_ListView.UnsubclassWindow(); bHandled = false; return 0; } LRESULT CDevicesDlg::OnListDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { if (m_ListView.GetSelectedCount() > 0) { ckmmc::Device *pDevice = reinterpret_cast(m_ListView.GetItemData( m_ListView.GetSelectedIndex())); ckcore::tstring Title = lngGetString(PROPERTIES_TITLE); Title += NDeviceUtil::GetDeviceName(*pDevice); CDeviceDlg DeviceDlg(*pDevice,Title.c_str()); DeviceDlg.DoModal(); } bHandled = false; return 0; } LRESULT CDevicesDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } LRESULT CDevicesDlg::OnRescan(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Empty the list view. m_ListView.DeleteAllItems(); // Rescan the bus. CWaitDlg WaitDlg; WaitDlg.Create(m_hWnd); WaitDlg.ShowWindow(SW_SHOW); ScanCallback Callback(WaitDlg); g_DeviceManager.scan(&Callback); WaitDlg.DestroyWindow(); // Fill the list view. FillListView(); return FALSE; } LRESULT CDevicesDlg::OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/device_configuration.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); return 0; } ================================================ FILE: src/app/dialog/devices_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "resource.h" #include "wait_dlg.hh" class CDevicesDlg : public CDialogImpl { private: class CInternalListViewCtrl : public CWindowImpl { public: BEGIN_MSG_MAP(CInternalListViewCtrl) MESSAGE_HANDLER(WM_KEYDOWN,OnKeyDown) END_MSG_MAP() CInternalListViewCtrl() { } LRESULT OnKeyDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { LRESULT lResult = DefWindowProc(uMsg,wParam,lParam); if (wParam == VK_RETURN) { if (GetSelectedCount() > 0) { ::MessageBox(NULL,_T(""),_T(""),MB_OK); } } return lResult; } }; class ScanCallback : public ckmmc::DeviceManager::ScanCallback { private: CWaitDlg &m_WaitDlg; public: ScanCallback(CWaitDlg &WaitDlg) : m_WaitDlg(WaitDlg) {} void event_status(ckmmc::DeviceManager::ScanCallback::Status Status); bool event_device(ckmmc::Device::Address &Addr); }; HIMAGELIST m_hListImageList; CInternalListViewCtrl m_ListView; bool Translate(); void InitializeListView(); void FillListView(); public: enum { IDD = IDD_DEVICESDLG }; CDevicesDlg(); ~CDevicesDlg(); BEGIN_MSG_MAP(CDevicesDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_DESTROY,OnDestroy) NOTIFY_HANDLER(IDC_DEVICELIST,NM_DBLCLK,OnListDblClick) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnOK) COMMAND_ID_HANDLER(IDC_RESCANBUTTON,OnRescan) COMMAND_HANDLER(IDC_HELPBUTTON,BN_CLICKED,OnHelp) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnDestroy(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnListDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnRescan(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/disc_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "disc_dlg.hh" CDiscDlg::CDiscDlg(const TCHAR *szTitle,const TCHAR *szDiscLabel,ckmmc::Device &Device) : CPropertySheetImpl(szTitle,0,NULL),m_GeneralPage(szDiscLabel,Device) { m_bCentered = false; m_psh.dwFlags |= PSH_NOAPPLYNOW | PSH_NOCONTEXTHELP; AddPage(m_GeneralPage); } CDiscDlg::~CDiscDlg() { } LRESULT CDiscDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } bHandled = FALSE; return 0; } ================================================ FILE: src/app/dialog/disc_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "disc_general_page.hh" class CDiscDlg : public CPropertySheetImpl { private: bool m_bCentered; CDiscGeneralPage m_GeneralPage; public: CDiscDlg(const TCHAR *szTitle,const TCHAR *szDiscLabel,ckmmc::Device &Device); ~CDiscDlg(); BEGIN_MSG_MAP(CDiscDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/disc_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "disc_general_page.hh" #include "string_table.hh" #include "lang_util.hh" #include "settings.hh" #include "trans_util.hh" #include "core2.hh" CDiscGeneralPage::CDiscGeneralPage(const TCHAR *szDiscLabel,ckmmc::Device &Device) : m_Device(Device) { m_hIcon = NULL; lstrcpy(m_szDiscLabel,szDiscLabel); // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_GENERAL,szStrValue)) SetTitle(szStrValue); } } } CDiscGeneralPage::~CDiscGeneralPage() { if (m_hIcon != NULL) DestroyIcon(m_hIcon); } bool CDiscGeneralPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a device translation section. if (!pLng->EnterSection(_T("disc"))) return false; // Translate. TCHAR *szStrValue; int iMaxStaticRight = 0; if (pLng->GetValuePtr(IDC_TYPELABELSTATIC,szStrValue)) { SetDlgItemText(IDC_TYPELABELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_TYPELABELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_BOOKLABELSTATIC,szStrValue)) { SetDlgItemText(IDC_BOOKLABELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_BOOKLABELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_REGIONLABELSTATIC,szStrValue)) { SetDlgItemText(IDC_REGIONLABELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_REGIONLABELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_LAYERLABELSTATIC,szStrValue)) { SetDlgItemText(IDC_LAYERLABELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_LAYERLABELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_TRACKLABELSTATIC,szStrValue)) { SetDlgItemText(IDC_TRACKLABELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_TRACKLABELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_SESSIONLABELSTATIC,szStrValue)) { SetDlgItemText(IDC_SESSIONLABELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_SESSIONLABELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_STATUSLABELSTATIC,szStrValue)) { SetDlgItemText(IDC_STATUSLABELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_STATUSLABELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_USEDSPACELABELSTATIC,szStrValue)) { SetDlgItemText(IDC_USEDSPACELABELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_USEDSPACELABELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_FREESPACELABELSTATIC,szStrValue)) { SetDlgItemText(IDC_FREESPACELABELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_FREESPACELABELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } // Make sure that the edit/combo controls are not in the way of the statics. if (iMaxStaticRight > 75) { UpdateEditPos(m_hWnd,IDC_TYPESTATIC,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_BOOKSTATIC,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_REGIONSTATIC,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_LAYERSTATIC,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_TRACKSTATIC,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_SESSIONSTATIC,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_STATUSSTATIC,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_USEDSPACESTATIC,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_FREESPACESTATIC,iMaxStaticRight); } return true; } void CDiscGeneralPage::DisplayDiscType(ckmmc::Device::Profile Profile) { switch (Profile) { case ckmmc::Device::ckPROFILE_CDROM: SetDlgItemText(IDC_TYPESTATIC,_T("CD-ROM")); break; case ckmmc::Device::ckPROFILE_CDR: SetDlgItemText(IDC_TYPESTATIC,_T("CD-R")); break; case ckmmc::Device::ckPROFILE_CDRW: SetDlgItemText(IDC_TYPESTATIC,_T("CD-RW")); break; case ckmmc::Device::ckPROFILE_DVDROM: SetDlgItemText(IDC_TYPESTATIC,_T("DVD-ROM")); break; case ckmmc::Device::ckPROFILE_DVDMINUSR_SEQ: SetDlgItemText(IDC_TYPESTATIC,_T("DVD-R")); break; case ckmmc::Device::ckPROFILE_DVDRAM: SetDlgItemText(IDC_TYPESTATIC,_T("DVD-RAM")); break; case ckmmc::Device::ckPROFILE_DVDMINUSRW_RESTOV: { TCHAR szBuffer[64]; lstrcpy(szBuffer,_T("DVD-RW ")); lstrcat(szBuffer,lngGetString(DISC_RESTRICTEDOVERWRITE)); SetDlgItemText(IDC_TYPESTATIC,szBuffer); } break; case ckmmc::Device::ckPROFILE_DVDMINUSRW_SEQ: { TCHAR szBuffer[64]; lstrcpy(szBuffer,_T("DVD-RW ")); lstrcat(szBuffer,lngGetString(DISC_SEQUENTIAL)); SetDlgItemText(IDC_TYPESTATIC,szBuffer); } break; case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_SEQ: case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_JUMP: SetDlgItemText(IDC_TYPESTATIC,_T("DVD-R DL")); break; case ckmmc::Device::ckPROFILE_DVDPLUSRW: SetDlgItemText(IDC_TYPESTATIC,_T("DVD+RW")); break; case ckmmc::Device::ckPROFILE_DVDPLUSR: SetDlgItemText(IDC_TYPESTATIC,_T("DVD+R")); break; case ckmmc::Device::ckPROFILE_DVDPLUSRW_DL: SetDlgItemText(IDC_TYPESTATIC,_T("DVD+RW DL")); break; case ckmmc::Device::ckPROFILE_DVDPLUSR_DL: SetDlgItemText(IDC_TYPESTATIC,_T("DVD+R DL")); break; case ckmmc::Device::ckPROFILE_BDROM: SetDlgItemText(IDC_TYPESTATIC,_T("BD-ROM")); break; case ckmmc::Device::ckPROFILE_BDR_SRM: SetDlgItemText(IDC_TYPESTATIC,_T("BD-R SRM")); break; case ckmmc::Device::ckPROFILE_BDR_RRM: SetDlgItemText(IDC_TYPESTATIC,_T("BD-R RRM")); break; case ckmmc::Device::ckPROFILE_BDRE: SetDlgItemText(IDC_TYPESTATIC,_T("BD-RE")); break; case ckmmc::Device::ckPROFILE_HDDVDROM: SetDlgItemText(IDC_TYPESTATIC,_T("HD DVD-ROM")); break; case ckmmc::Device::ckPROFILE_HDDVDR: SetDlgItemText(IDC_TYPESTATIC,_T("HD DVD-R")); break; case ckmmc::Device::ckPROFILE_HDDVDRAM: SetDlgItemText(IDC_TYPESTATIC,_T("HD DVD-RAM")); break; default: SetDlgItemText(IDC_TYPESTATIC,lngGetString(DISC_UNKNOWN)); break; } } void CDiscGeneralPage::DisplayBookType(unsigned char ucBookType,unsigned char ucBookRev) { TCHAR szBookType[64]; switch (ucBookType) { case 0: lsprintf(szBookType,_T("DVD-ROM (%s %d)"),lngGetString(DISC_REVISION),ucBookRev); break; case 1: lsprintf(szBookType,_T("DVD-RAM (%s %d)"),lngGetString(DISC_REVISION),ucBookRev); break; case 2: lsprintf(szBookType,_T("DVD-R (%s %d)"),lngGetString(DISC_REVISION),ucBookRev); break; case 3: lsprintf(szBookType,_T("DVD-RW (%s %d)"),lngGetString(DISC_REVISION),ucBookRev); break; case 9: lsprintf(szBookType,_T("DVD+RW (%s %d)"),lngGetString(DISC_REVISION),ucBookRev); break; case 10: lsprintf(szBookType,_T("DVD+R (%s %d)"),lngGetString(DISC_REVISION),ucBookRev); break; case 14: lsprintf(szBookType,_T("DVD+R DL (%s %d)"),lngGetString(DISC_REVISION),ucBookRev); break; default: lsprintf(szBookType,lngGetString(DISC_UNKNOWN)); break; } SetDlgItemText(IDC_BOOKSTATIC,szBookType); } void CDiscGeneralPage::DisplayStatus(CCore2DiscInfo *pDiscInfo) { const TCHAR *szDiscStatus = _T(""); const TCHAR *szSessionStatus = _T(""); switch (pDiscInfo->m_ucDiscStatus) { case CCore2DiscInfo::DS_EMTPY: szDiscStatus = lngGetString(DISC_BLANK); break; case CCore2DiscInfo::DS_INCOMPLETE: szDiscStatus = lngGetString(DISC_INCOMPLETE); break; case CCore2DiscInfo::DS_FINALIZED: szDiscStatus = lngGetString(DISC_FIXATED); break; case CCore2DiscInfo::DS_RANDOMACCESS: szDiscStatus = lngGetString(DISC_RANDOMACCESS); break; } switch (pDiscInfo->m_ucLastSessStatus) { case CCore2DiscInfo::LSS_EMTPY: szSessionStatus = lngGetString(DISC_EMPTY); break; case CCore2DiscInfo::LSS_INCOMPLETE: szSessionStatus = lngGetString(DISC_INCOMPLETE); break; case CCore2DiscInfo::LSS_RESERVED: szSessionStatus = lngGetString(DISC_RESERVED); break; case CCore2DiscInfo::LSS_COMPLETE: szSessionStatus = lngGetString(DISC_COMPLETE); break; } TCHAR szStatus[256]; lsprintf(szStatus,lngGetString(DISC_STATUS),szDiscStatus,szSessionStatus, pDiscInfo->m_ucFlags & CCore2DiscInfo::FLAG_ERASABLE ? _T("") : lngGetString(DISC_NOT)); SetDlgItemText(IDC_STATUSSTATIC,szStatus); } LRESULT CDiscGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Create the icon. HINSTANCE hInstance = LoadLibrary(_T("shell32.dll")); m_hIcon = (HICON)LoadImage(hInstance,MAKEINTRESOURCE(12),IMAGE_ICON,GetSystemMetrics(SM_CXICON),GetSystemMetrics(SM_CYICON),LR_DEFAULTCOLOR); FreeLibrary(hInstance); SendMessage(GetDlgItem(IDC_ICONSTATIC),STM_SETICON,(WPARAM)m_hIcon,0L); // Display the information. SetDlgItemText(IDC_NAMESTATIC,m_szDiscLabel); CCore2Info Info; ckmmc::Device::Profile Profile = m_Device.profile(); DisplayDiscType(Profile); // Extra DVD information. unsigned int uiNumLayers = 0; TCHAR szSmallBuffer[64]; if (Profile == ckmmc::Device::ckPROFILE_DVDROM || Profile == ckmmc::Device::ckPROFILE_DVDMINUSR_SEQ || Profile == ckmmc::Device::ckPROFILE_DVDRAM || Profile == ckmmc::Device::ckPROFILE_DVDMINUSRW_RESTOV || Profile == ckmmc::Device::ckPROFILE_DVDMINUSRW_SEQ || Profile == ckmmc::Device::ckPROFILE_DVDMINUSR_DL_SEQ || Profile == ckmmc::Device::ckPROFILE_DVDMINUSR_DL_JUMP || Profile == ckmmc::Device::ckPROFILE_DVDPLUSRW || Profile == ckmmc::Device::ckPROFILE_DVDPLUSR || Profile == ckmmc::Device::ckPROFILE_DVDPLUSRW_DL || Profile == ckmmc::Device::ckPROFILE_DVDPLUSR_DL) { // Book type. CCore2PhysFmtInfo PhysInfo; if (Info.ReadPhysFmtInfo(m_Device,&PhysInfo)) DisplayBookType(PhysInfo.m_ucDiscCategory,PhysInfo.m_ucPartVersion); else SetDlgItemText(IDC_BOOKSTATIC,lngGetString(DISC_UNKNOWN)); // Region. unsigned char ucRegion = 0; if (Info.GetDiscDVDRegion(m_Device,ucRegion)) { if (ucRegion == 0) SetDlgItemText(IDC_REGIONSTATIC,lngGetString(DISC_NOREGION)); else { lsprintf(szSmallBuffer,_T("%d"),(int)ucRegion); SetDlgItemText(IDC_REGIONSTATIC,szSmallBuffer); } } else SetDlgItemText(IDC_REGIONSTATIC,lngGetString(DISC_UNKNOWN)); // Layers lsprintf(szSmallBuffer,_T("%d"),uiNumLayers); SetDlgItemText(IDC_LAYERSTATIC,szSmallBuffer); } else { // Book type. SetDlgItemText(IDC_BOOKSTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_BOOKSTATIC),false); ::EnableWindow(GetDlgItem(IDC_BOOKLABELSTATIC),false); // Region. SetDlgItemText(IDC_REGIONSTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_REGIONSTATIC),false); ::EnableWindow(GetDlgItem(IDC_REGIONLABELSTATIC),false); // Layers. SetDlgItemText(IDC_LAYERSTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_LAYERSTATIC),false); ::EnableWindow(GetDlgItem(IDC_LAYERLABELSTATIC),false); } CCore2DiscInfo DiscInfo; if (Info.ReadDiscInformation(m_Device,&DiscInfo)) { // Tracks. lsprintf(szSmallBuffer,_T("%d"),DiscInfo.m_usLastSessLstTrack - (DiscInfo.m_usLastSessFstTrack - 1)); SetDlgItemText(IDC_TRACKSTATIC,szSmallBuffer); // Sessions. lsprintf(szSmallBuffer,_T("%d"),DiscInfo.m_usNumSessions); SetDlgItemText(IDC_SESSIONSTATIC,szSmallBuffer); // Status. DisplayStatus(&DiscInfo); // Space. unsigned __int64 uiUsedSize = 0; unsigned __int64 uiFreeSize = 0; if (Info.GetTotalDiscCapacity(m_Device,uiUsedSize,uiFreeSize)) { FormatBytes(szSmallBuffer,uiUsedSize); lsprintf(szSmallBuffer + lstrlen(szSmallBuffer),_T(" (%I64d Bytes)"),uiUsedSize); SetDlgItemText(IDC_USEDSPACESTATIC,szSmallBuffer); FormatBytes(szSmallBuffer,uiFreeSize); lsprintf(szSmallBuffer + lstrlen(szSmallBuffer),_T(" (%I64d Bytes)"),uiFreeSize); SetDlgItemText(IDC_FREESPACESTATIC,szSmallBuffer); } else { // Used space. SetDlgItemText(IDC_USEDSPACESTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_USEDSPACESTATIC),false); ::EnableWindow(GetDlgItem(IDC_USEDSPACELABELSTATIC),false); // Free space. SetDlgItemText(IDC_FREESPACESTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_FREESPACESTATIC),false); ::EnableWindow(GetDlgItem(IDC_FREESPACELABELSTATIC),false); } } else { // Tracks. SetDlgItemText(IDC_TRACKSTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_TRACKSTATIC),false); ::EnableWindow(GetDlgItem(IDC_TRACKLABELSTATIC),false); // Sessions. SetDlgItemText(IDC_SESSIONSTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_SESSIONSTATIC),false); ::EnableWindow(GetDlgItem(IDC_SESSIONLABELSTATIC),false); // Status. SetDlgItemText(IDC_STATUSSTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_STATUSSTATIC),false); ::EnableWindow(GetDlgItem(IDC_STATUSLABELSTATIC),false); // Used space. SetDlgItemText(IDC_USEDSPACESTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_USEDSPACESTATIC),false); ::EnableWindow(GetDlgItem(IDC_USEDSPACELABELSTATIC),false); // Free space. SetDlgItemText(IDC_FREESPACESTATIC,lngGetString(DISC_UNKNOWN)); ::EnableWindow(GetDlgItem(IDC_FREESPACESTATIC),false); ::EnableWindow(GetDlgItem(IDC_FREESPACELABELSTATIC),false); } // Translate the window. Translate(); return TRUE; } ================================================ FILE: src/app/dialog/disc_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "resource.h" #include "core2_info.hh" class CDiscGeneralPage : public CPropertyPageImpl { private: HICON m_hIcon; ckmmc::Device &m_Device; TCHAR m_szDiscLabel[64]; bool Translate(); void DisplayDiscType(ckmmc::Device::Profile Profile); void DisplayBookType(unsigned char ucBookType,unsigned char ucBookRev); void DisplayStatus(CCore2DiscInfo *pDiscInfo); public: enum { IDD = IDD_PROPPAGE_DISCGENERAL }; CDiscGeneralPage(const TCHAR *szDiscLabel,ckmmc::Device &Device); ~CDiscGeneralPage(); BEGIN_MSG_MAP(CDiscGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/edit_track_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "edit_track_dlg.hh" #include "string_table.hh" #include "settings.hh" CEditTrackDlg::CEditTrackDlg(CItemData *pItemData) { m_pItemData = pItemData; } CEditTrackDlg::~CEditTrackDlg() { } bool CEditTrackDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a edittrack translation section. if (!pLng->EnterSection(_T("edittrack"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDC_TITLESTATIC,szStrValue)) SetDlgItemText(IDC_TITLESTATIC,szStrValue); if (pLng->GetValuePtr(IDC_ARTISTSTATIC,szStrValue)) SetDlgItemText(IDC_ARTISTSTATIC,szStrValue); return true; } LRESULT CEditTrackDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); SetWindowText((TCHAR *)lParam); SetDlgItemText(IDC_TITLEEDIT,m_pItemData->GetAudioData()->szTrackTitle); SetDlgItemText(IDC_ARTISTEDIT,m_pItemData->GetAudioData()->szTrackArtist); // Translate the window. Translate(); return TRUE; } LRESULT CEditTrackDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { GetDlgItemText(IDC_TITLEEDIT,m_pItemData->GetAudioData()->szTrackTitle,159); GetDlgItemText(IDC_ARTISTEDIT,m_pItemData->GetAudioData()->szTrackArtist,159); EndDialog(wID); return FALSE; } LRESULT CEditTrackDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } ================================================ FILE: src/app/dialog/edit_track_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "tree_manager.hh" class CEditTrackDlg : public CDialogImpl { private: CItemData *m_pItemData; bool Translate(); public: enum { IDD = IDD_EDITTRACKDLG }; CEditTrackDlg(CItemData *pItemData); ~CEditTrackDlg(); BEGIN_MSG_MAP(CEditTrackDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/erase_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "infrarecorder.hh" #include "erase_dlg.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" #include "device_util.hh" #include "core2_util.hh" #include "version.hh" #include "visual_styles.hh" CEraseDlg::CEraseDlg(bool bAppMode) { m_bAppMode = bAppMode; m_hRefreshIcon = NULL; m_hRefreshImageList = NULL; m_uiRecorderTextLen = 0; } CEraseDlg::~CEraseDlg() { if (m_hRefreshImageList != NULL) ImageList_Destroy(m_hRefreshImageList); if (m_hRefreshIcon != NULL) DestroyIcon(m_hRefreshIcon); } bool CEraseDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is an erase translation section. if (!pLng->EnterSection(_T("erase"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDD_ERASEDLG,szStrValue)) // Title. SetWindowText(szStrValue); if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDC_HELPBUTTON,szStrValue)) SetDlgItemText(IDC_HELPBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_RECORDERSTATIC,szStrValue)) SetDlgItemText(IDC_RECORDERSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_METHODSTATIC,szStrValue)) SetDlgItemText(IDC_METHODSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_FORCECHECK,szStrValue)) SetDlgItemText(IDC_FORCECHECK,szStrValue); if (pLng->GetValuePtr(IDC_EJECTCHECK,szStrValue)) SetDlgItemText(IDC_EJECTCHECK,szStrValue); if (pLng->GetValuePtr(IDC_SIMULATECHECK,szStrValue)) SetDlgItemText(IDC_SIMULATECHECK,szStrValue); if (pLng->GetValuePtr(IDC_SPEEDSTATIC,szStrValue)) SetDlgItemText(IDC_SPEEDSTATIC,szStrValue); return true; } bool CEraseDlg::InitRecorderMedia() { if (m_uiRecorderTextLen == 0) m_uiRecorderTextLen = ::GetWindowTextLength(GetDlgItem(IDC_RECORDERSTATIC)); TCHAR szBuffer[256]; ::GetWindowText(GetDlgItem(IDC_RECORDERSTATIC),szBuffer,m_uiRecorderTextLen + 1); // Empty the method combo box. m_MethodCombo.ResetContent(); ckmmc::Device &Device = *reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); Device.refresh(); // Get current profile. bool bSupportedProfile = false; ckmmc::Device::Profile Profile = Device.profile(); switch (Profile) { case ckmmc::Device::ckPROFILE_CDRW: m_MethodCombo.AddString(lngGetString(BLANKMODE_FULL)); m_MethodCombo.AddString(lngGetString(BLANKMODE_MINIMAL)); m_MethodCombo.AddString(lngGetString(BLANKMODE_UNCLOSE)); m_MethodCombo.AddString(lngGetString(BLANKMODE_SESSION)); m_MethodCombo.SetItemData(0,CCore2::ERASE_BLANK_FULL); m_MethodCombo.SetItemData(1,CCore2::ERASE_BLANK_MINIMAL); m_MethodCombo.SetItemData(2,CCore2::ERASE_BLANK_UNCLOSE); m_MethodCombo.SetItemData(3,CCore2::ERASE_BLANK_SESSION); m_MethodCombo.SetCurSel(0); bSupportedProfile = true; // Enable simulation if supported by the recorder. ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK), Device.support(ckmmc::Device::ckDEVICE_TEST_WRITE)); // Enable force erase. ::EnableWindow(GetDlgItem(IDC_FORCECHECK),FALSE); break; case ckmmc::Device::ckPROFILE_DVDPLUSRW: case ckmmc::Device::ckPROFILE_DVDPLUSRW_DL: m_MethodCombo.AddString(lngGetString(FORMATMODE_QUICK)); m_MethodCombo.AddString(lngGetString(FORMATMODE_FULL)); m_MethodCombo.SetItemData(0,CCore2::ERASE_FORMAT_QUICK); m_MethodCombo.SetItemData(1,CCore2::ERASE_FORMAT_FULL); m_MethodCombo.SetCurSel(1); bSupportedProfile = true; // Disable simulation (not supported for DVD+RW media). ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK),FALSE); // Disable force erase. ::EnableWindow(GetDlgItem(IDC_FORCECHECK),FALSE); break; case ckmmc::Device::ckPROFILE_DVDRAM: m_MethodCombo.AddString(lngGetString(FORMATMODE_FULL)); m_MethodCombo.SetItemData(0,CCore2::ERASE_FORMAT_FULL); m_MethodCombo.SetCurSel(0); bSupportedProfile = true; // Disable simulation (not supported for DVD-RAM media). ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK),FALSE); // Disable force erase. ::EnableWindow(GetDlgItem(IDC_FORCECHECK),FALSE); break; case ckmmc::Device::ckPROFILE_DVDMINUSRW_RESTOV: case ckmmc::Device::ckPROFILE_DVDMINUSRW_SEQ: m_MethodCombo.AddString(lngGetString(FORMATMODE_QUICK)); m_MethodCombo.AddString(lngGetString(FORMATMODE_FULL)); m_MethodCombo.AddString(lngGetString(BLANKMODE_FULL)); m_MethodCombo.AddString(lngGetString(BLANKMODE_MINIMAL)); m_MethodCombo.AddString(lngGetString(BLANKMODE_UNCLOSE)); m_MethodCombo.AddString(lngGetString(BLANKMODE_SESSION)); m_MethodCombo.SetItemData(0,CCore2::ERASE_FORMAT_QUICK); m_MethodCombo.SetItemData(1,CCore2::ERASE_FORMAT_FULL); m_MethodCombo.SetItemData(2,CCore2::ERASE_BLANK_FULL); m_MethodCombo.SetItemData(3,CCore2::ERASE_BLANK_MINIMAL); m_MethodCombo.SetItemData(4,CCore2::ERASE_BLANK_UNCLOSE); m_MethodCombo.SetItemData(5,CCore2::ERASE_BLANK_SESSION); m_MethodCombo.SetCurSel(2); bSupportedProfile = true; // Disable simulation (not supported for DVD-RW media). ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK),FALSE); // Disable force erase. ::EnableWindow(GetDlgItem(IDC_FORCECHECK),FALSE); break; case ckmmc::Device::ckPROFILE_NONE: m_MethodCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_MethodCombo.SetCurSel(0); lstrcat(szBuffer,_T(" ")); lstrcat(szBuffer,lngGetString(MEDIA_INSERT)); break; default: m_MethodCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_MethodCombo.SetCurSel(0); lstrcat(szBuffer,_T(" ")); lstrcat(szBuffer,lngGetString(MEDIA_UNSUPPORTED)); break; } ::SetWindowText(GetDlgItem(IDC_RECORDERSTATIC),szBuffer); // Maximum write speed. m_SpeedCombo.ResetContent(); m_SpeedCombo.AddString(lngGetString(MISC_MAXIMUM)); m_SpeedCombo.SetItemData(0,0xFFFFFFFF); m_SpeedCombo.SetCurSel(0); // General if (bSupportedProfile) { m_MethodCombo.EnableWindow(TRUE); m_SpeedCombo.EnableWindow(TRUE); ::EnableWindow(GetDlgItem(IDOK),TRUE); ::EnableWindow(GetDlgItem(IDC_METHODSTATIC),TRUE); ::EnableWindow(GetDlgItem(IDC_SPEEDSTATIC),TRUE); const std::vector &WriteSpeeds = Device.write_speeds(); std::vector::const_iterator it; for (it = WriteSpeeds.begin(); it != WriteSpeeds.end(); it++) { m_SpeedCombo.AddString(ckmmc::util::kb_to_disp_speed(*it,Profile).c_str()); m_SpeedCombo.SetItemData(m_SpeedCombo.GetCount() - 1, static_cast(ckmmc::util::kb_to_human_speed(*it, ckmmc::Device::ckPROFILE_CDR))); } } else { m_MethodCombo.EnableWindow(FALSE); m_SpeedCombo.EnableWindow(FALSE); ::EnableWindow(GetDlgItem(IDOK),FALSE); ::EnableWindow(GetDlgItem(IDC_METHODSTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_SPEEDSTATIC),FALSE); } return true; } void CEraseDlg::InitRefreshButton() { m_hRefreshIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_REFRESHICON),IMAGE_ICON,16,16,LR_DEFAULTCOLOR); // In Windows XP there is a bug causing the button to loose it's themed style if // assigned an icon. The solution to this is to assign an image list instead. if (g_WinVer.m_ulMajorCCVersion >= 6) { // Get color depth (minimum requirement is 32-bits for alpha blended images). int iBitsPixel = GetDeviceCaps(::GetDC(HWND_DESKTOP),BITSPIXEL); m_hRefreshImageList = ImageList_Create(16,16,ILC_COLOR32 | (iBitsPixel < 32 ? ILC_MASK : 0),0,1); ImageList_AddIcon(m_hRefreshImageList,m_hRefreshIcon); BUTTON_IMAGELIST bImageList; bImageList.himl = m_hRefreshImageList; bImageList.margin.left = 0; bImageList.margin.top = 0; bImageList.margin.right = 0; bImageList.margin.bottom = 0; bImageList.uAlign = BUTTON_IMAGELIST_ALIGN_CENTER; SendMessage(GetDlgItem(IDC_REFRESHBUTTON),BCM_SETIMAGELIST,0,(LPARAM)&bImageList); } else { SendMessage(GetDlgItem(IDC_REFRESHBUTTON),BM_SETIMAGE,IMAGE_ICON,(LPARAM)m_hRefreshIcon); } // If the application is themed, then adjust the size of the button. if (g_VisualStyles.IsThemeActive()) { RECT rcButton; ::GetWindowRect(GetDlgItem(IDC_REFRESHBUTTON),&rcButton); ScreenToClient(&rcButton); ::SetWindowPos(GetDlgItem(IDC_REFRESHBUTTON),NULL,rcButton.left - 1,rcButton.top - 1, rcButton.right - rcButton.left + 2,rcButton.bottom - rcButton.top + 2,0); } } void CEraseDlg::CheckRecorderMedia() { if (!InitRecorderMedia()) { // Method. m_MethodCombo.ResetContent(); m_MethodCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_MethodCombo.SetCurSel(0); // Write speed. m_SpeedCombo.ResetContent(); m_SpeedCombo.AddString(lngGetString(MISC_MAXIMUM)); m_SpeedCombo.SetCurSel(0); m_MethodCombo.EnableWindow(FALSE); m_SpeedCombo.EnableWindow(FALSE); ::EnableWindow(GetDlgItem(IDOK),FALSE); ::EnableWindow(GetDlgItem(IDC_METHODSTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_SPEEDSTATIC),FALSE); } } LRESULT CEraseDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); if (m_bAppMode) { ModifyStyle(0,WS_MINIMIZEBOX | WS_SYSMENU); ModifyStyleEx(0,WS_EX_APPWINDOW); HMENU hSysMenu = GetSystemMenu(FALSE); ::InsertMenu(hSysMenu,0,MF_BYPOSITION,SC_RESTORE,_T("&Restore")); ::InsertMenu(hSysMenu,2,MF_BYPOSITION,SC_MINIMIZE,_T("Mi&nimize")); ::InsertMenu(hSysMenu,3,MF_BYPOSITION | MF_SEPARATOR,0,_T("")); } m_RecorderCombo = GetDlgItem(IDC_RECORDERCOMBO); m_MethodCombo = GetDlgItem(IDC_METHODCOMBO); m_SpeedCombo = GetDlgItem(IDC_SPEEDCOMBO); // Set the refresh button icon. InitRefreshButton(); // Recorder combo box. std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; // We only want to add recorder to the list. if (!pDevice->recorder()) continue; m_RecorderCombo.AddString(NDeviceUtil::GetDeviceName(*pDevice).c_str()); m_RecorderCombo.SetItemData(m_RecorderCombo.GetCount() - 1, reinterpret_cast(pDevice)); } if (m_RecorderCombo.GetCount() == 0) { m_RecorderCombo.AddString(lngGetString(FAILURE_NORECORDERS)); m_RecorderCombo.EnableWindow(false); m_RecorderCombo.SetCurSel(0); // Disable the OK button. ::EnableWindow(GetDlgItem(IDOK),false); } else { m_RecorderCombo.SetCurSel(0); BOOL bDummy; OnRecorderChange(NULL,NULL,NULL,bDummy); } // Setup the default settings. m_MethodCombo.SetCurSel(g_EraseSettings.m_iMode); CheckDlgButton(IDC_FORCECHECK,g_EraseSettings.m_bForce); CheckDlgButton(IDC_EJECTCHECK,g_EraseSettings.m_bEject); CheckDlgButton(IDC_SIMULATECHECK,g_EraseSettings.m_bSimulate); // Translate the window. Translate(); // Initialize the drive media. CheckRecorderMedia(); return TRUE; } LRESULT CEraseDlg::OnTimer(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { ckmmc::Device *pDevice = reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); // Check for media change. if (g_Core2.CheckMediaChange(*pDevice)) CheckRecorderMedia(); return TRUE; } LRESULT CEraseDlg::OnRecorderChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Kill any already running timers. ::KillTimer(m_hWnd,TIMER_ID); ::SetTimer(m_hWnd,TIMER_ID,TIMER_INTERVAL,NULL); // Initialize the drive media. CheckRecorderMedia(); bHandled = false; return 0; } LRESULT CEraseDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Remember the configuration. g_EraseSettings.m_iMode = (int)m_MethodCombo.GetItemData(m_MethodCombo.GetCurSel()); g_EraseSettings.m_bForce = IsDlgButtonChecked(IDC_FORCECHECK) == TRUE; g_EraseSettings.m_bEject = IsDlgButtonChecked(IDC_EJECTCHECK) == TRUE; g_EraseSettings.m_bSimulate = IsDlgButtonChecked(IDC_SIMULATECHECK) == TRUE; // For internal use only. g_EraseSettings.m_pRecorder = reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); g_EraseSettings.m_uiSpeed = (unsigned int)m_SpeedCombo.GetItemData(m_SpeedCombo.GetCurSel()); EndDialog(wID); return FALSE; } LRESULT CEraseDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } LRESULT CEraseDlg::OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/erase_disc.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); return 0; } LRESULT CEraseDlg::OnRefresh(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Initialize the drive media. CheckRecorderMedia(); return 0; } ================================================ FILE: src/app/dialog/erase_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "resource.h" #include "core2.hh" class CEraseDlg : public CDialogImpl { private: bool m_bAppMode; HICON m_hRefreshIcon; HIMAGELIST m_hRefreshImageList; unsigned int m_uiRecorderTextLen; CComboBox m_RecorderCombo; CComboBox m_MethodCombo; CComboBox m_SpeedCombo; enum { TIMER_ID = 42, TIMER_INTERVAL = 1000 }; bool Translate(); bool InitRecorderMedia(); void InitRefreshButton(); void CheckRecorderMedia(); public: enum { IDD = IDD_ERASEDLG }; CEraseDlg(bool bAppMode); ~CEraseDlg(); BEGIN_MSG_MAP(CEraseDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_TIMER,OnTimer) COMMAND_HANDLER(IDC_RECORDERCOMBO,CBN_SELCHANGE,OnRecorderChange) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) COMMAND_HANDLER(IDC_HELPBUTTON,BN_CLICKED,OnHelp) COMMAND_HANDLER(IDC_REFRESHBUTTON,BN_CLICKED,OnRefresh) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnTimer(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnRecorderChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnRefresh(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/fixate_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "infrarecorder.hh" #include "string_table.hh" #include "device_util.hh" #include "settings.hh" #include "lang_util.hh" #include "fixate_dlg.hh" CFixateDlg::CFixateDlg(bool bAppMode) { m_bAppMode = bAppMode; } CFixateDlg::~CFixateDlg() { } bool CFixateDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // This dialog shares many strings with the erase dialog so we begin // borrow strings from the erase section. if (!pLng->EnterSection(_T("erase"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDC_HELPBUTTON,szStrValue)) SetDlgItemText(IDC_HELPBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_RECORDERSTATIC,szStrValue)) SetDlgItemText(IDC_RECORDERSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_SIMULATECHECK,szStrValue)) SetDlgItemText(IDC_SIMULATECHECK,szStrValue); if (!pLng->EnterSection(_T("fixate"))) return false; if (pLng->GetValuePtr(IDD_FIXATEDLG,szStrValue)) // Title. SetWindowText(szStrValue); if (pLng->GetValuePtr(IDC_EJECTCHECK,szStrValue)) SetDlgItemText(IDC_EJECTCHECK,szStrValue); return true; } LRESULT CFixateDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); if (m_bAppMode) { ModifyStyle(0,WS_MINIMIZEBOX | WS_SYSMENU); ModifyStyleEx(0,WS_EX_APPWINDOW); HMENU hSysMenu = GetSystemMenu(FALSE); ::InsertMenu(hSysMenu,0,MF_BYPOSITION,SC_RESTORE,_T("&Restore")); ::InsertMenu(hSysMenu,2,MF_BYPOSITION,SC_MINIMIZE,_T("Mi&nimize")); ::InsertMenu(hSysMenu,3,MF_BYPOSITION | MF_SEPARATOR,0,_T("")); } m_RecorderCombo = GetDlgItem(IDC_RECORDERCOMBO); // Recorder combo box. std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; // We only want to add recorder to the list. if (!pDevice->recorder()) continue; m_RecorderCombo.AddString(NDeviceUtil::GetDeviceName(*pDevice).c_str()); m_RecorderCombo.SetItemData(m_RecorderCombo.GetCount() - 1, reinterpret_cast(pDevice)); } if (m_RecorderCombo.GetCount() == 0) { m_RecorderCombo.AddString(lngGetString(FAILURE_NORECORDERS)); m_RecorderCombo.EnableWindow(false); // Disable the OK button. ::EnableWindow(GetDlgItem(IDOK),false); } m_RecorderCombo.SetCurSel(0); // Enable/disable the simulation checkbox depending on if the selected recorder // supports that operation. ckmmc::Device *pDevice = reinterpret_cast(m_RecorderCombo.GetItemData(0)); ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK), pDevice->support(ckmmc::Device::ckDEVICE_TEST_WRITE)); // Setup the default settings. CheckDlgButton(IDC_EJECTCHECK,g_FixateSettings.m_bEject); CheckDlgButton(IDC_SIMULATECHECK,g_FixateSettings.m_bSimulate); // Translate the window. Translate(); return TRUE; } LRESULT CFixateDlg::OnRecorderChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Enable/disable the simulation checkbox depending on if the selected recorder // supports that operation. ckmmc::Device *pDevice = reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); ::EnableWindow(GetDlgItem(IDC_SIMULATECHECK), pDevice->support(ckmmc::Device::ckDEVICE_TEST_WRITE)); bHandled = false; return 0; } LRESULT CFixateDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Remember the configuration. g_FixateSettings.m_bEject = IsDlgButtonChecked(IDC_EJECTCHECK) == 1; g_FixateSettings.m_bSimulate = IsDlgButtonChecked(IDC_SIMULATECHECK) == 1; // For internal use only. g_FixateSettings.m_pRecorder = reinterpret_cast(m_RecorderCombo.GetItemData( m_RecorderCombo.GetCurSel())); EndDialog(wID); return FALSE; } LRESULT CFixateDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } LRESULT CFixateDlg::OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/fixate_disc.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); return 0; } ================================================ FILE: src/app/dialog/fixate_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CFixateDlg : public CDialogImpl { private: bool m_bAppMode; CComboBox m_RecorderCombo; bool Translate(); public: enum { IDD = IDD_FIXATEDLG }; CFixateDlg(bool bAppMode); ~CFixateDlg(); BEGIN_MSG_MAP(CFixateDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_HANDLER(IDC_RECORDERCOMBO,CBN_SELCHANGE,OnRecorderChange) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) COMMAND_HANDLER(IDC_HELPBUTTON,BN_CLICKED,OnHelp) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnRecorderChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/import_session_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" #include "wait_dlg.hh" #include "scsi.hh" #include "device_util.hh" #include "core2_info.hh" #include "log_dlg.hh" #include "infrarecorder.hh" #include "import_session_dlg.hh" CImportSessionDlg::CImportSessionDlg() : m_pSelDevice(NULL),m_pSelTrackData(NULL) { } CImportSessionDlg::~CImportSessionDlg() { // Delete any track data. ResetDiscInfo(); } bool CImportSessionDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is an erase translation section. if (!pLng->EnterSection(_T("importsession"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDD_IMPORTSESSIONDLG,szStrValue)) // Title. SetWindowText(szStrValue); if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDC_DRIVESTATIC,szStrValue)) SetDlgItemText(IDC_DRIVESTATIC,szStrValue); if (pLng->GetValuePtr(IDC_USEDSPACELABELSTATIC,szStrValue)) SetDlgItemText(IDC_USEDSPACELABELSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_TRACKSTATIC,szStrValue)) SetDlgItemText(IDC_TRACKSTATIC,szStrValue); return true; } bool CImportSessionDlg::UpdateDiscInfo(ckmmc::Device &Device) { g_pLogDlg->print_line(_T("CImportSessionDlg::UpdateDiscInfo")); unsigned char ucFirstTrackNumber = 0,ucLastTrackNumber = 0; std::vector Tracks; CCore2Info Info; if (Info.ReadTOC(Device,ucFirstTrackNumber,ucLastTrackNumber,Tracks)) { g_pLogDlg->print_line(_T(" First and last disc track number: %d, %d."), ucFirstTrackNumber,ucLastTrackNumber); // Iterate through all tracks. CCore2TrackInfo TrackInfo; std::vector::const_iterator itTrack; for (itTrack = Tracks.begin(); itTrack != Tracks.end(); itTrack++) { if (!Info.ReadTrackInformation(Device,CCore2Info::TIT_LBA,itTrack->m_ulTrackAddr,&TrackInfo)) { g_pLogDlg->print_line(_T(" Error: Unable to read information about track %d."),itTrack->m_ucTrackNumber); return false; } // Always assume a post-gap of 150 sectors. This may be a bad idea. unsigned long ulTrackSize = TrackInfo.m_ulTrackSize - 150; m_TrackData.push_back(new CTrackData(TrackInfo.m_ucDataMode,TrackInfo.m_usSessionNumber, TrackInfo.m_usTrackNumber,itTrack->m_ulTrackAddr,ulTrackSize)); } } else { g_pLogDlg->print_line(_T(" Error: Unable to read TOC information to validate selected track.")); return false; } return true; } void CImportSessionDlg::ResetDiscInfo() { std::vector::iterator itTrack; for (itTrack = m_TrackData.begin(); itTrack != m_TrackData.end(); itTrack++) delete *itTrack; m_TrackData.clear(); } LRESULT CImportSessionDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); m_DeviceCombo = GetDlgItem(IDC_DEVICECOMBO); m_TrackCombo = GetDlgItem(IDC_TRACKCOMBO); // Device combo box. std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { const ckmmc::Device *pDevice = *it; m_DeviceCombo.AddString(NDeviceUtil::GetDeviceName(*pDevice).c_str()); m_DeviceCombo.SetItemData(m_DeviceCombo.GetCount() - 1, reinterpret_cast(pDevice)); } if (m_DeviceCombo.GetCount() == 0) { m_DeviceCombo.AddString(lngGetString(FAILURE_NORECORDERS)); m_DeviceCombo.EnableWindow(false); // Disable the OK button. ::EnableWindow(GetDlgItem(IDOK),false); } m_DeviceCombo.SetCurSel(0); // Translate the window. Translate(); // Update the information. if (m_DeviceCombo.GetCount() > 0) { BOOL bDymmy; OnDeviceChange(NULL,NULL,NULL,bDymmy); } return TRUE; } LRESULT CImportSessionDlg::OnDeviceChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { bHandled = false; ckmmc::Device *pDevice = reinterpret_cast(m_DeviceCombo.GetItemData( m_DeviceCombo.GetCurSel())); // Rescan the bus. CWaitDlg WaitDlg; WaitDlg.Create(m_hWnd); WaitDlg.ShowWindow(SW_SHOW); // Initialize device. WaitDlg.SetMessage(lngGetString(INIT_DEVICECD)); CCore2Info Info; CCore2DiscInfo DiscInfo; if (Info.ReadDiscInformation(*pDevice,&DiscInfo)) { // UPDATE: This does not seem to work on DVD+RW discs. //::EnableWindow(GetDlgItem(IDOK),DiscInfo.m_ucDiscStatus == CCore2DiscInfo::DS_INCOMPLETE); ::EnableWindow(GetDlgItem(IDOK),TRUE); // Space. unsigned __int64 uiUsedBytes = 0; unsigned __int64 uiFreeBytes = 0; if (Info.GetTotalDiscCapacity(*pDevice,uiUsedBytes,uiFreeBytes)) { m_uiAllocatedSize = uiUsedBytes; TCHAR szBuffer[64]; FormatBytes(szBuffer,m_uiAllocatedSize); lsprintf(szBuffer + lstrlen(szBuffer),_T(" (%I64d Bytes)"),m_uiAllocatedSize); SetDlgItemText(IDC_USEDSPACESTATIC,szBuffer); } else { SetDlgItemText(IDC_USEDSPACESTATIC,lngGetString(DISC_UNKNOWN)); } // Delete any previous track data. ResetDiscInfo(); UpdateDiscInfo(*pDevice); m_TrackCombo.ResetContent(); if (m_TrackData.size() == 0) { m_TrackCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_TrackCombo.EnableWindow(FALSE); ::EnableWindow(GetDlgItem(IDOK),FALSE); } else { m_TrackCombo.EnableWindow(TRUE); TCHAR szBuffer[128]; std::vector::iterator itTrack; for (itTrack = m_TrackData.begin(); itTrack != m_TrackData.end(); itTrack++) { lsnprintf_s(szBuffer,sizeof(szBuffer)/sizeof(TCHAR),_T("%s %u %s %u: %u-%u (%s %u)"), lngGetString(MISC_SESSION),(*itTrack)->m_usSessionNumber, lngGetString(MISC_TRACK),(*itTrack)->m_usTrackNumber, (*itTrack)->m_ulTrackAddr,(*itTrack)->m_ulTrackAddr + (*itTrack)->m_ulTrackLen, lngGetString(MISC_MODE),(*itTrack)->m_ucMode); m_TrackCombo.AddString(szBuffer); m_TrackCombo.SetItemData(m_TrackCombo.GetCount() - 1,(DWORD_PTR)*itTrack); } ::EnableWindow(GetDlgItem(IDOK),TRUE); } m_TrackCombo.SetCurSel(m_TrackCombo.GetCount() - 1); } else { ResetDiscInfo(); m_TrackCombo.ResetContent(); m_TrackCombo.AddString(lngGetString(MISC_NOTAVAILABLE)); m_TrackCombo.SetCurSel(0); m_TrackCombo.EnableWindow(FALSE); ::EnableWindow(GetDlgItem(IDOK),false); SetDlgItemText(IDC_USEDSPACESTATIC,lngGetString(DISC_UNKNOWN)); } WaitDlg.DestroyWindow(); return 0; } LRESULT CImportSessionDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { m_pSelDevice = reinterpret_cast(m_DeviceCombo.GetItemData( m_DeviceCombo.GetCurSel())); m_pSelTrackData = (CTrackData *)m_TrackCombo.GetItemData(m_TrackCombo.GetCurSel()); EndDialog(wID); return FALSE; } LRESULT CImportSessionDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } ================================================ FILE: src/app/dialog/import_session_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "resource.h" class CImportSessionDlg : public CDialogImpl { private: class CTrackData { public: unsigned char m_ucMode; unsigned short m_usSessionNumber; unsigned short m_usTrackNumber; unsigned long m_ulTrackAddr; unsigned long m_ulTrackLen; CTrackData(unsigned char ucMode,unsigned short usSessionNumber, unsigned short usTrackNumber,unsigned long ulTrackAddr,unsigned long ulTrackLen) : m_ucMode(ucMode),m_usSessionNumber(usSessionNumber),m_usTrackNumber(usTrackNumber), m_ulTrackAddr(ulTrackAddr),m_ulTrackLen(ulTrackLen) { } }; std::vector m_TrackData; CComboBox m_DeviceCombo; CComboBox m_TrackCombo; bool Translate(); bool UpdateDiscInfo(ckmmc::Device &Device); void ResetDiscInfo(); public: enum { IDD = IDD_IMPORTSESSIONDLG }; // Data members that can be accessed from another object when the dialog // has closed. unsigned __int64 m_uiAllocatedSize; ckmmc::Device *m_pSelDevice; CTrackData *m_pSelTrackData; CImportSessionDlg(); ~CImportSessionDlg(); BEGIN_MSG_MAP(CImportSessionDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_HANDLER(IDC_DEVICECOMBO,CBN_SELCHANGE,OnDeviceChange) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) REFLECT_NOTIFICATIONS() END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnDeviceChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/info_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "info_dlg.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" CInfoDlg::CInfoDlg(bool *pRemember,const TCHAR *szMessage,int iFlags) { m_pRemember = pRemember; m_iFlags = iFlags; n_szMessage = szMessage; } CInfoDlg::~CInfoDlg() { } bool CInfoDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; TCHAR *szStrValue; // Translate the title. if (!pLng->EnterSection(_T("strings"))) return false; // Translate the rest. if (!pLng->EnterSection(_T("info"))) return false; if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDC_DISPLAYMSGCHECK,szStrValue)) SetDlgItemText(IDC_DISPLAYMSGCHECK,szStrValue); return true; } /* CInfoDlg::InitializeMessage --------------------------- Sets the text of the static control to szMessage. Resizes the static to fit all of the text, and if necessary also moves the check box and resizes the main window. */ void CInfoDlg::InitializeMessage(const TCHAR *szMessage) { // Set the message text. SetDlgItemText(IDC_INFOSTATIC,szMessage); // Get handles. HWND hMessageCtrl = GetDlgItem(IDC_INFOSTATIC); HWND hCheckCtrl = GetDlgItem(IDC_DISPLAYMSGCHECK); HDC hMessageDC = ::GetDC(hMessageCtrl); // Perpare font. HFONT hMessageFont = (HFONT)::SendMessage(hMessageCtrl,WM_GETFONT,0,0); HFONT hOldFont = (HFONT)::SelectObject(hMessageDC,hMessageFont); // Calculate and set the message size. RECT rcMessage; ::GetWindowRect(GetDlgItem(IDC_INFOSTATIC),&rcMessage); ScreenToClient(&rcMessage); RECT rcText; rcText.left = 0; rcText.right = rcMessage.right - rcMessage.left; int iMessageHeight = DrawText(hMessageDC,szMessage,lstrlen(szMessage),&rcText,DT_LEFT | DT_CALCRECT | DT_WORDBREAK); ::MoveWindow(GetDlgItem(IDC_INFOSTATIC),rcMessage.left,rcMessage.top,rcMessage.right - rcMessage.left,iMessageHeight,TRUE); // Restore old font. ::SelectObject(hMessageDC,hOldFont); // Move the check box and resize the window if necessary. RECT rcCheck; ::GetWindowRect(hCheckCtrl,&rcCheck); ScreenToClient(&rcCheck); int iNewCheckTop = rcMessage.top + iMessageHeight + 8; if (iNewCheckTop > rcCheck.top) { ::SetWindowPos(hCheckCtrl,0, rcCheck.left,iNewCheckTop,rcCheck.right - rcCheck.left,rcCheck.bottom - rcCheck.top,0); int iDiff = iNewCheckTop - rcCheck.top; // Resize the main window. RECT rcWindow; GetWindowRect(&rcWindow); MoveWindow(rcWindow.left,rcWindow.top, rcWindow.right - rcWindow.left,rcWindow.bottom - rcWindow.top + iDiff); } } LRESULT CInfoDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); // Set the icon and window text. HANDLE hIcon; if (m_iFlags & INFODLG_ICONERROR) { hIcon = LoadIcon(NULL,IDI_HAND); SetWindowText(lngGetString(GENERAL_ERROR)); } else if (m_iFlags & INFODLG_ICONWARNING) { hIcon = LoadIcon(NULL,IDI_EXCLAMATION); SetWindowText(lngGetString(GENERAL_WARNING)); } else { hIcon = LoadIcon(NULL,IDI_ASTERISK); SetWindowText(lngGetString(GENERAL_INFORMATION)); } ::SendMessage(GetDlgItem(IDC_ICONSTATIC),STM_SETICON,(WPARAM)hIcon,0L); // Translate the window. Translate(); // Display message and caculate correct messsage and window widths. InitializeMessage(n_szMessage); // Disable the cancel button if necessary. if (m_iFlags & INFODLG_NOCANCEL) ::EnableWindow(GetDlgItem(IDCANCEL),FALSE); return TRUE; } LRESULT CInfoDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { *m_pRemember = !IsDlgButtonChecked(IDC_DISPLAYMSGCHECK) == TRUE; EndDialog(wID); return FALSE; } LRESULT CInfoDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } ================================================ FILE: src/app/dialog/info_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" // Flags. #define INFODLG_NOCANCEL 1 #define INFODLG_ICONERROR 2 #define INFODLG_ICONWARNING 4 class CInfoDlg : public CDialogImpl { private: // Pointer to the value that will be changed according to the "Do not display // this message again" option. bool *m_pRemember; int m_iFlags; // Pointer to the message text to be displayed. const TCHAR *n_szMessage; bool Translate(); void InitializeMessage(const TCHAR *szMessage); public: enum { IDD = IDD_INFODLG }; CInfoDlg(bool *pRemember,const TCHAR *szMessage,int iFlags = 0); ~CInfoDlg(); BEGIN_MSG_MAP(CEraseDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/log_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "string_table.hh" #include "lang_util.hh" #include "settings.hh" #include "diagnostics.hh" #include "version.hh" #include "log_dlg.hh" // FIXME: No arrow is used, not enough space. CLogDlg::CLogDlg() : m_DiagButton(IDR_DIAGNOSTICSMENU,false), m_LogFile(GetLogFullPath()) { } CLogDlg::~CLogDlg() { } ckcore::Path CLogDlg::GetLogFullPath() { // Get system date. SYSTEMTIME st; GetLocalTime(&st); TCHAR szFileName[13]; GetDateFormat(LOCALE_USER_DEFAULT,0,&st,_T("yyMMdd"),szFileName,7); // Get the log dir path. ckcore::Path DirPath = GetLogDirPath(); // Create the file path if it doesn't exist. ckcore::Directory::create(DirPath); // Construct the file name. lstrcat(szFileName,_T(".log")); // Append the file name and return. return DirPath + szFileName; } ckcore::Path CLogDlg::GetLogDirPath() { TCHAR szDirPath[MAX_PATH]; #ifdef PORTABLE GetModuleFileName(NULL,szDirPath,MAX_PATH - 1); ExtractFilePath(szDirPath); lstrcat(szDirPath,_T("logs\\")); #else if (SUCCEEDED(SHGetFolderPath(m_hWnd,CSIDL_APPDATA | CSIDL_FLAG_CREATE,NULL, SHGFP_TYPE_CURRENT,szDirPath))) { IncludeTrailingBackslash(szDirPath); lstrcat(szDirPath,_T("InfraRecorder\\logs\\")); } else { GetModuleFileName(NULL,szDirPath,MAX_PATH - 1); ExtractFilePath(szDirPath); } #endif return ckcore::Path(szDirPath); } void CLogDlg::InitializeLogFile() { if (m_LogFile.exist()) { if (m_LogFile.open(ckcore::File::ckOPEN_READWRITE)) { m_LogFile.seek(0,ckcore::File::ckFILE_END); m_LogFile.write(ckT("\r\n"),sizeof(ckcore::tchar) << 1); } } else { if (m_LogFile.open(ckcore::File::ckOPEN_WRITE)) { // Write byte order mark. unsigned short usBOM = BOM_UTF32BE; m_LogFile.write(&usBOM,2); } } } bool CLogDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a log translation section. if (!pLng->EnterSection(_T("log"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDD_LOGDLG,szStrValue)) // Title. SetWindowText(szStrValue); if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(ID_SAVEASBUTTON,szStrValue)) SetDlgItemText(ID_SAVEASBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_FILESBUTTON,szStrValue)) SetDlgItemText(IDC_FILESBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_DIAGNOSTICSBUTTON,szStrValue)) SetDlgItemText(IDC_DIAGNOSTICSBUTTON,szStrValue); // Modify the diagnostics popup menu. if (pLng->GetValuePtr(ID_DIAGNOSTICS_DEVICESCAN,szStrValue)) ModifyMenu(m_DiagButton.GetMenu(),ID_DIAGNOSTICS_DEVICESCAN,MF_BYCOMMAND | MF_STRING, ID_DIAGNOSTICS_DEVICESCAN,(LPCTSTR)szStrValue); return true; } /* CLogDlg::Show ------------- Should be called when the log should be displayed. This function automaticly scrolls to the bottom of the log. */ void CLogDlg::Show() { g_pLogDlg->ShowWindow(SW_SHOW); m_LogEdit.LineScroll(m_LogEdit.GetLineCount()); } void CLogDlg::print(const TCHAR *szString,...) { if (g_GlobalSettings.m_bLog && IsWindow()) { va_list args; va_start(args,szString); _vsnwprintf(m_szLineBuffer,LOG_LINEBUFFER_SIZE - 1,szString,args); m_LogEdit.AppendText(m_szLineBuffer); // Write to the log file. if (m_LogFile.test()) m_LogFile.write(m_szLineBuffer,lstrlen(m_szLineBuffer) * sizeof(TCHAR)); } } void CLogDlg::print_line(const TCHAR *szLine,...) { if (g_GlobalSettings.m_bLog && IsWindow()) { va_list args; va_start(args,szLine); _vsnwprintf(m_szLineBuffer,LOG_LINEBUFFER_SIZE - 1,szLine,args); m_LogEdit.AppendText(m_szLineBuffer); m_LogEdit.AppendText(_T("\r\n")); // Write to the log file. if (m_LogFile.test()) { m_LogFile.write(m_szLineBuffer,lstrlen(m_szLineBuffer) * sizeof(TCHAR)); m_LogFile.write(ckT("\r\n"),2 * sizeof(ckcore::tchar)); } } } bool CLogDlg::SaveLog(const TCHAR *szFileName) { ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_WRITE)) return false; // Obtain buffer handle. HLOCAL hBuffer = m_LogEdit.GetHandle(); if (hBuffer == NULL) return false; // A special unicode hack is needed here since the edit might be in unicode // while the application is not. unsigned char *pBuffer = (unsigned char *)LocalLock(hBuffer); unsigned int uiTextLength = m_LogEdit.GetWindowTextLength(); bool bIsUnicode = ::IsWindowUnicode(m_LogEdit) == TRUE; #ifdef LOG_SAVE_BOM if (bIsUnicode) { unsigned short usBOM = BOM_UTF32BE; if (File.write(&usBOM,2) == -1) { File.remove(); return false; } } #endif // Do the actual writing. unsigned int uiRemaining = uiTextLength * (bIsUnicode ? 2 : 1); while (uiRemaining > LOG_WRITEBUFFER_SIZE) { if (File.write(pBuffer,LOG_WRITEBUFFER_SIZE) == -1) { File.remove(); return false; } uiRemaining -= LOG_WRITEBUFFER_SIZE; pBuffer += LOG_WRITEBUFFER_SIZE; } if (File.write(pBuffer,uiRemaining) == -1) { File.remove(); return false; } LocalUnlock(hBuffer); return true; } LRESULT CLogDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); DlgResize_Init(true,true,WS_CLIPCHILDREN); m_LogEdit = GetDlgItem(IDC_LOGEDIT); // The edit control can hold a maximum of 30,000 characters by default, // and that's too little when for example the ISO 9600 file system starts // generating warnings for many files in the project. const UINT uiMaxCharCount = 1 * 1024 * 1024; m_LogEdit.SetLimitText(uiMaxCharCount); // There is no error indication, so manually check that the new value // was actually accepted. ATLASSERT(uiMaxCharCount == m_LogEdit.GetLimitText()); m_DiagButton.SubclassWindow(GetDlgItem(IDC_DIAGNOSTICSBUTTON)); // Initialize the log. if (g_GlobalSettings.m_bLog) { // Initialize the log file. InitializeLogFile(); // Print version information. TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); unsigned long ulDummy; unsigned long ulDataSize = GetFileVersionInfoSize(szFileName,&ulDummy); if (ulDataSize != 0) { unsigned char *pBlock = new unsigned char[ulDataSize]; struct LANGANDCODEPAGE { unsigned short usLanguage; unsigned short usCodePage; } *pTranslate; if (GetFileVersionInfo(szFileName,NULL,ulDataSize,pBlock) > 0) { // Get language information (only one language should be present). VerQueryValue(pBlock,_T("\\VarFileInfo\\Translation"), (LPVOID *)&pTranslate,(unsigned int *)&ulDummy); // Calculate the FileVersion sub block path. TCHAR szStrBuffer[128]; lsprintf(szStrBuffer,_T("\\StringFileInfo\\%04x%04x\\FileVersion"), pTranslate[0].usLanguage,pTranslate[0].usCodePage); unsigned char *pBuffer; VerQueryValue(pBlock,szStrBuffer,(LPVOID *)&pBuffer,(unsigned int *)&ulDataSize); print(_T("InfraRecorder version %s"),(TCHAR *)pBuffer); } delete [] pBlock; } #ifdef _M_IA64 print_line(_T(" (IA64)")); #elif defined _M_X64 print_line(_T(" (x64)")); #else print_line(_T(" (x86)")); #endif // Date and time. SYSTEMTIME st; GetLocalTime(&st); TCHAR szDate[64]; GetDateFormat(LOCALE_USER_DEFAULT,0,&st,_T("dddd, MMMM dd yyyy "),szDate,64); TCHAR szDateTime[128]; lsprintf(szDateTime,_T("Started: %s%.2d:%.2d:%.2d."),szDate,st.wHour,st.wMinute,st.wSecond); print_line(szDateTime); // Windows version. print_line(_T("Versions: MSW = %d.%d, IE = %d.%d, CC = %d.%d."), g_WinVer.m_ulMajorVersion,g_WinVer.m_ulMinorVersion, g_WinVer.m_ulMajorIEVersion,g_WinVer.m_ulMinorIEVersion, g_WinVer.m_ulMajorCCVersion,g_WinVer.m_ulMinorCCVersion); } // Translate the window. Translate(); return TRUE; } LRESULT CLogDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { ShowWindow(SW_HIDE); return FALSE; } LRESULT CLogDlg::OnSaveAs(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { WTL::CFileDialog FileDialog(false,_T("txt"),_T("Untitled"),OFN_EXPLORER | OFN_HIDEREADONLY, _T("Text Documents (*.txt)\0*.txt\0All Files (*.*)\0*.*\0\0"),m_hWnd); if (FileDialog.DoModal() == IDOK) { if (!SaveLog(FileDialog.m_szFileName)) lngMessageBox(m_hWnd,ERROR_FILEWRITE,GENERAL_ERROR,MB_OK | MB_ICONERROR); } return FALSE; } LRESULT CLogDlg::OnFiles(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { ckcore::Path Path = GetLogDirPath(); ShellExecute(HWND_DESKTOP,_T("open"),_T("explorer.exe"),Path.name().c_str(),NULL,SW_SHOWDEFAULT); return 0; } LRESULT CLogDlg::OnDiagDeviceScan(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_Diagnostics.DeviceScan(); return 0; } ================================================ FILE: src/app/dialog/log_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include #include #include "drop_down_button.hh" #define BOM_UTF8 0xEFBBBF #define BOM_UTF32BE 0x0000FEFF #define BOM_UTF32LE 0xFFFE0000 #define BOM_SCSU 0x0EFEFF #define LOG_SAVE_BOM #define LOG_WRITEBUFFER_SIZE 1024 #define LOG_LINEBUFFER_SIZE 512 class CLogDlg : public CDialogImpl,public CDialogResize, public ckcore::Log { private: CEdit m_LogEdit; CDropDownButton m_DiagButton; // This buffer will be used when creating the log line by the variable // argument list. TCHAR m_szLineBuffer[LOG_LINEBUFFER_SIZE]; ckcore::File m_LogFile; ckcore::Path GetLogFullPath(); ckcore::Path GetLogDirPath(); void InitializeLogFile(); bool Translate(); bool SaveLog(const TCHAR *szFileName); public: enum { IDD = IDD_LOGDLG }; CLogDlg(); ~CLogDlg(); void Show(); void print(const TCHAR *szString,...); void print_line(const TCHAR *szLine,...); // Resize maps. BEGIN_DLGRESIZE_MAP(CLogDlg) DLGRESIZE_CONTROL(IDOK,DLSZ_MOVE_X) DLGRESIZE_CONTROL(ID_SAVEASBUTTON,DLSZ_MOVE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_DIAGNOSTICSBUTTON,DLSZ_MOVE_X) DLGRESIZE_CONTROL(IDC_FILESBUTTON,DLSZ_MOVE_X) DLGRESIZE_CONTROL(IDC_LOGEDIT,DLSZ_SIZE_X | DLSZ_SIZE_Y) END_DLGRESIZE_MAP() // Events. BEGIN_MSG_MAP(CLogDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnOK) COMMAND_ID_HANDLER(ID_SAVEASBUTTON,OnSaveAs) COMMAND_ID_HANDLER(IDC_FILESBUTTON,OnFiles) COMMAND_ID_HANDLER(ID_DIAGNOSTICS_DEVICESCAN,OnDiagDeviceScan) REFLECT_NOTIFICATIONS() CHAIN_MSG_MAP(CDialogResize) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnSaveAs(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnDiagDeviceScan(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFiles(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; extern CLogDlg * g_pLogDlg; ================================================ FILE: src/app/dialog/main_frm.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include #include #include "resource.h" #include "settings.hh" #include "registry.hh" #include "log_dlg.hh" #include "devices_dlg.hh" #include "infrarecorder.hh" #include "core.hh" #include "core2.hh" #include "settings_manager.hh" #include "string_table.hh" #include "tree_manager.hh" #include "version.hh" #include "project_prop_dlg.hh" #include "lang_util.hh" #include "config_dlg.hh" #include "action_manager.hh" #include "disc_dlg.hh" #include "scsi.hh" #include "import_session_dlg.hh" #include "core2_stream.hh" #include "project_drop_source.hh" #include "files_data_object.hh" #include "device_util.hh" #include "about_window.hh" #include "main_frm.hh" CMainFrame::CMainFrame() : m_pShellListView(NULL),m_bWelcomePane(false) { m_iDefaultProjType = PROJECTTYPE_DATA; m_iDefaultMedia = -1; // Use default for each project type. m_bDefaultProjDVDVideo = false; m_bDefaultWizard = true; // Empty the file name. m_szProjectFile[0] = '\0'; m_hMainSmallImageList = NULL; m_hMainLargeImageList = NULL; m_hMiniToolBarImageList = NULL; // By default we allow the tree selection to change. m_bEnableTreeSelection = true; // By default we don't ignore accelerators. m_bEnableAccel = true; } CMainFrame::~CMainFrame() { } /* CMainFrame::AutoRunCheck ------------------------ Checks if autorun is enabled. Windows polls the CD drive periodically, which may result in recording failure. */ /*void CMainFrame::AutoRunCheck() { CRegistry Reg; Reg.SetRoot(HKEY_LOCAL_MACHINE); if (Reg.OpenKey(_T("SYSTEM\\CurrentControlSet\\Services\\Cdrom\\"),false)) { bool bAutoRun = false; if (Reg.ReadBool(_T("AutoRun"),bAutoRun)) { if (bAutoRun) { if (lngMessageBox(m_hWnd,CONFIRM_AUTORUNENABLED,GENERAL_WARNING,MB_YESNO | MB_ICONWARNING) == IDYES) { if (!Reg.WriteBool(_T("AutoRun"),false)) lngMessageBox(m_hWnd,ERROR_REGISTRYWRITE,GENERAL_ERROR,MB_OK | MB_ICONERROR); } } } Reg.CloseKey(); } }*/ /* CMainFrame::EnableAutoRun ------------------------- Enabled or decible the Windows CD-ROM autorun feature. It returns the old registry setting. */ bool CMainFrame::EnableAutoRun(bool bEnable) { bool bResult = false; CRegistry Reg; Reg.SetRoot(HKEY_LOCAL_MACHINE); if (Reg.OpenKey(_T("SYSTEM\\CurrentControlSet\\Services\\Cdrom\\"),false)) { Reg.ReadBool(_T("AutoRun"),bResult); Reg.WriteBool(_T("AutoRun"),bEnable); Reg.CloseKey(); } return bResult; } HWND CMainFrame::CreateToolBarCtrl() { unsigned long ulToolBarStyle = g_DynamicSettings.m_iToolBarText == TOOLBAR_TEXT_SHOWRIGHT ? TBSTYLE_LIST : 0; HWND hWndToolBar = m_ToolBar.Create(m_hWnd,rcDefault,NULL,ATL_SIMPLE_TOOLBAR_PANE_STYLE | CCS_ADJUSTABLE | ulToolBarStyle,NULL,ATL_IDW_TOOLBAR); m_ToolBar.SetExtendedStyle(TBSTYLE_EX_DRAWDDARROWS); m_ToolBar.SetImageList(g_DynamicSettings.m_iToolBarIcon == TOOLBAR_ICON_SMALL ? m_hMainSmallImageList : m_hMainLargeImageList); // Add all toolbar buttons. g_ToolBarManager.FillToolBarCtrl(&m_ToolBar); return hWndToolBar; } int CMainFrame::GetDefaultMedia() { if (m_iDefaultMedia != -1) return m_iDefaultMedia; // Find which recorder that the media was changed for. std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; // Check if the current device was affected. if (pDevice->recorder()) { CCore2Info Info; CCore2DiscInfo DiscInfo; // Fetch media information. if (Info.ReadDiscInformation(*pDevice,&DiscInfo) && DiscInfo.m_ucDiscStatus == CCore2DiscInfo::DS_EMTPY) { switch (pDevice->profile()) { case ckmmc::Device::ckPROFILE_DVDRAM: case ckmmc::Device::ckPROFILE_DVDPLUSRW: case ckmmc::Device::ckPROFILE_DVDMINUSRW_RESTOV: case ckmmc::Device::ckPROFILE_DVDMINUSRW_SEQ: case ckmmc::Device::ckPROFILE_DVDMINUSR_SEQ: case ckmmc::Device::ckPROFILE_DVDPLUSR: return SPACEMETER_SIZE_DVD; case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_SEQ: case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_JUMP: case ckmmc::Device::ckPROFILE_DVDPLUSRW_DL: case ckmmc::Device::ckPROFILE_DVDPLUSR_DL: return SPACEMETER_SIZE_DLDVD; /*case ckmmc::Device::ckPROFILE_BDROM: case ckmmc::Device::ckPROFILE_BDR_SRM: case ckmmc::Device::ckPROFILE_BDR_RRM: case ckmmc::Device::ckPROFILE_BDRE: case ckmmc::Device::ckPROFILE_HDDVDROM: case ckmmc::Device::ckPROFILE_HDDVDR: case ckmmc::Device::ckPROFILE_HDDVDRAM: return;*/ // FIXME: In order to switch to CD size we need to know exactly how much the blank CD can store. /*case ckmmc::Device::ckPROFILE_CDR: case ckmmc::Device::ckPROFILE_CDRW: return SPACEMETER_SIZE_703MB;*/ } } } } return -1; } void CMainFrame::InitializeMainSmallImageList() { // Create the image list. HBITMAP hSmallBitmap,hLargeBitmap; // Get color depth (minimum requirement is 32-bits for alpha blended images). int iBitsPixel = GetDeviceCaps(::GetDC(HWND_DESKTOP),BITSPIXEL); if (g_WinVer.m_ulMajorCCVersion >= 6 && iBitsPixel >= 32) { hSmallBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MAINSMALLBITMAP)); m_hMainSmallImageList = ImageList_Create(16,16,ILC_COLOR32,0,19); ImageList_Add(m_hMainSmallImageList,hSmallBitmap,NULL); hLargeBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MAINLARGEBITMAP)); m_hMainLargeImageList = ImageList_Create(32,32,ILC_COLOR32,0,19); ImageList_Add(m_hMainLargeImageList,hLargeBitmap,NULL); } else { hSmallBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MAINSMALLBITMAP_)); m_hMainSmallImageList = ImageList_Create(16,16,ILC_COLOR32 | ILC_MASK,0,19); ImageList_AddMasked(m_hMainSmallImageList,hSmallBitmap,RGB(255,0,255)); hLargeBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MAINLARGEBITMAP_)); m_hMainLargeImageList = ImageList_Create(32,32,ILC_COLOR32 | ILC_MASK,0,19); ImageList_AddMasked(m_hMainLargeImageList,hLargeBitmap,RGB(255,0,255)); } DeleteObject(hSmallBitmap); DeleteObject(hLargeBitmap); } void CMainFrame::InitializeMiniToolBarImageList() { // Create the image list. HBITMAP hBitmap; // Get color depth (minimum requirement is 32-bits for alpha blended images). int iBitsPixel = GetDeviceCaps(::GetDC(HWND_DESKTOP),BITSPIXEL); if (g_WinVer.m_ulMajorCCVersion >= 6 && iBitsPixel >= 32) { hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MINITOOLBARBITMAP)); m_hMiniToolBarImageList = ImageList_Create(16,16,ILC_COLOR32,0,6); ImageList_Add(m_hMiniToolBarImageList,hBitmap,NULL); } else { hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MINITOOLBARBITMAP_)); m_hMiniToolBarImageList = ImageList_Create(16,16,ILC_COLOR32 | ILC_MASK,0,6); ImageList_AddMasked(m_hMiniToolBarImageList,hBitmap,RGB(255,0,255)); } DeleteObject(hBitmap); } void CMainFrame::InitializeMainView() { m_hWndClient = m_SpaceMeterView.Create(m_hWnd,rcDefault, NULL,WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,WS_EX_CONTROLPARENT); m_SpaceMeterView.m_cxySplitBar = 2; // Force the splitter size 2, Vista uses a larger size by default. m_SpaceMeterView.SetSplitterExtendedStyle(SPLIT_NONINTERACTIVE | SPLIT_BOTTOMALIGNED); // Space meter. m_SpaceMeter.Create(m_SpaceMeterView,rcDefault,NULL,WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN); m_SpaceMeter.Initialize(); // Main view. m_MainView.Create(m_SpaceMeterView,rcDefault,NULL,WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,WS_EX_CONTROLPARENT); m_MainView.m_cxySplitBar = 4; // Force the splitter size 2, Vista uses a larger size by default. UpdateLayout(); // FIXME: m_WelcomePane.Create(m_SpaceMeterView,rcDefault,NULL, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | WS_TABSTOP, WS_EX_CLIENTEDGE); // Update the splitter origins. RECT rcClient; ::GetClientRect(m_hWndClient,&rcClient); if (m_bDefaultWizard) { m_bWelcomePane = true; m_SpaceMeterView.SetSplitterPane(SPLIT_PANE_TOP,m_WelcomePane); m_SpaceMeterView.SetSinglePaneMode(SPLIT_PANE_TOP); } else { m_SpaceMeterView.SetSplitterPane(SPLIT_PANE_BOTTOM,m_SpaceMeter); m_SpaceMeterView.SetSplitterPane(SPLIT_PANE_TOP,m_MainView); m_SpaceMeterView.SetSplitterPos(rcClient.bottom - rcClient.top - MAINFRAME_SPACEMETER_HEIGHT); } m_MainView.SetSplitterPos((rcClient.bottom - rcClient.top - MAINFRAME_SPACEMETER_HEIGHT)/2); } bool CMainFrame::InitializeShellTreeView() { // Get the handle of the system image list. SHFILEINFO shFileInfo; HIMAGELIST hImageListSmall = (HIMAGELIST)SHGetFileInfo(_T("C:\\"),0, &shFileInfo,sizeof(SHFILEINFO),SHGFI_SYSICONINDEX | SHGFI_SMALLICON); IShellFolder *pDesktop; ITEMIDLIST *pidl; TV_ITEM tvItem = { 0 }; TV_INSERTSTRUCT tvInsert = { 0 }; // Assign the image list handle and set the scroll time. m_ShellTreeView.SetImageList(hImageListSmall,LVSIL_NORMAL); m_ShellTreeView.SetScrollTime(100); // Get the location of the desktop folder. if (SUCCEEDED(SHGetSpecialFolderLocation(NULL,CSIDL_DESKTOP,&pidl))) { if (FAILED(SHGetDesktopFolder(&pDesktop))) { // Free the pidl. IMalloc *pMalloc; if (SUCCEEDED(SHGetMalloc(&pMalloc))) pMalloc->Free(pidl); return false; } CShellTreeItemInfo *pItemInfo = new CShellTreeItemInfo; if (pItemInfo == NULL) { // Free the pidl IMalloc *pMalloc; if (SUCCEEDED(SHGetMalloc(&pMalloc))) pMalloc->Free(pidl); pDesktop->Release(); return false; } // On the root node pidlSelf is offcourse equal to pidlFullyQual. pItemInfo->pidlSelf = pidl; pItemInfo->pidlFullyQual = pidl; // Set the tree view item parameters. tvItem.mask = TVIF_PARAM | TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_CHILDREN; tvItem.lParam = (LPARAM)pItemInfo; tvItem.pszText = LPSTR_TEXTCALLBACK; tvItem.iImage = tvItem.iSelectedImage = I_IMAGECALLBACK; tvItem.cChildren = TRUE; tvInsert.item = tvItem; tvInsert.hInsertAfter = TVI_LAST; // Insert the root item in the tree and expand it to insert its contents. HTREEITEM hItem = m_ShellTreeView.InsertItem(&tvInsert); m_ShellTreeView.Expand(hItem); // Check if the selected folder is the desktop. In that case we should go // to the dekstop root, not the :/Documents and Settings//Desktop // folder. TCHAR szDesktopPath[MAX_PATH]; m_PidlHelp.GetPathName(pidl,szDesktopPath); if (!lstrcmp(szDesktopPath,g_DynamicSettings.m_szShellDir)) { m_ShellTreeView.SelectItem(hItem); } else { // The selected folder is not the desktop. OpenFolder(g_DynamicSettings.m_szShellDir,hItem,true); CShellTreeItemInfo *pItemInfo2 = (CShellTreeItemInfo *)m_ShellTreeView.GetItemData(m_ShellTreeView.GetSelectedItem()); if (pItemInfo2->dwFlags == 0) { if (pItemInfo2->pParentFolder == 0) m_pShellListView->BrowseObject(pItemInfo2->pidlSelf,SBSP_SAMEBROWSER | SBSP_ABSOLUTE); else m_pShellListView->BrowseObject(pItemInfo2->pidlFullyQual,SBSP_SAMEBROWSER | SBSP_ABSOLUTE); } } pDesktop->Release(); // Register the directory monitor. if (!m_DirectoryMonitor.Register(m_hWnd,WM_SHELLCHANGE,SHCNE_MKDIR | SHCNE_RENAMEFOLDER | SHCNE_RMDIR,pidl,true)) { MessageBox(_T("An error occured when trying to register the directory monitor. As a result the InfraRecorder explorer tree will not automatically synchronize with Windows Explorer."),_T("Error"),MB_OK | MB_ICONERROR); } } return true; } void CMainFrame::InitializeExplorerView(unsigned int uiSplitterPos) { m_ExplorerView.Create(m_MainView,rcDefault, NULL,WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,WS_EX_CONTROLPARENT); m_ExplorerView.m_cxySplitBar = 4; // Force the splitter size 2, Vista uses a larger size by default. UpdateLayout(); m_MainView.SetSplitterPane(SPLIT_PANE_TOP,m_ExplorerView); m_ExplorerView.SetSplitterPos(uiSplitterPos); // Create the list view container. m_ShellListViewContainer.Create(m_ExplorerView,rcDefault,NULL, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,WS_EX_CONTROLPARENT,(unsigned int)0,NULL); m_ShellListViewContainer.SetImageList(m_hMiniToolBarImageList); // Add container buttons. m_ShellListViewContainer.AddToolBarButton(ID_VIEW_UPLEVEL,0); m_ShellListViewContainer.AddToolBarSeparator(); m_ShellListViewContainer.AddToolBarButton(ID_ADD_SELECTED,1); m_ShellListViewContainer.AddToolBarButton(ID_ADD_ALL,2); m_ShellListViewContainer.UpdateToolBar(); // Create the shell list view. m_pShellListView = new CShellListViewCtrl(m_ShellListViewContainer,m_hWnd); m_ShellListViewContainer.SetClient(*m_pShellListView); // Create the tree view container. m_ShellTreeViewContainer.Create(m_ExplorerView,rcDefault,NULL, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,WS_EX_CONTROLPARENT,(unsigned int)0,NULL); m_ShellTreeViewContainer.SetHeaderHeight(m_ShellListViewContainer.GetHeaderHeight()); m_ShellTreeViewContainer.SetLabelText(lngGetString(TITLE_EXPLORERVIEW)); // Create the shell tree view. m_ShellTreeView.Create(m_ShellTreeViewContainer,rcDefault,NULL, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | WS_TABSTOP | TVS_HASLINES | TVS_LINESATROOT | TVS_HASBUTTONS | TVS_SHOWSELALWAYS, WS_EX_CLIENTEDGE,IDC_SHELLTREEVIEW); m_ShellTreeViewContainer.SetClient(m_ShellTreeView); // Setup the view. m_ExplorerView.SetSplitterPane(SPLIT_PANE_LEFT,m_ShellTreeViewContainer); m_ExplorerView.SetSplitterPane(SPLIT_PANE_RIGHT,m_ShellListViewContainer); // Initialize the shell tree view. InitializeShellTreeView(); } void CMainFrame::InitializeProjectView(unsigned int uiSplitterPos) { m_ProjectView.Create(m_MainView,rcDefault, NULL,WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,WS_EX_CONTROLPARENT); m_ProjectView.m_cxySplitBar = 4; // Force the splitter size 2, Vista uses a larger size by default. UpdateLayout(); m_MainView.SetSplitterPane(SPLIT_PANE_BOTTOM,m_ProjectView); m_ProjectView.SetSplitterPos(uiSplitterPos); // Create the list view container. m_ProjectListViewContainer.Create(m_ProjectView,rcDefault,NULL, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,WS_EX_CONTROLPARENT,(unsigned int)0,NULL); m_ProjectListViewContainer.SetImageList(m_hMiniToolBarImageList); // Add container buttons. m_ProjectListViewContainer.AddToolBarButton(ID_VIEW_UPLEVEL,0); m_ProjectListViewContainer.AddToolBarSeparator(); m_ProjectListViewContainer.AddToolBarButton(ID_EDIT_NEWFOLDER,4); m_ProjectListViewContainer.AddToolBarButton(ID_EDIT_RENAME,5); m_ProjectListViewContainer.AddToolBarSeparator(); m_ProjectListViewContainer.AddToolBarButton(ID_EDIT_REMOVE,3); m_ProjectListViewContainer.UpdateToolBar(); // Create the list view. m_ProjectListView.Create(m_ProjectListViewContainer,rcDefault,NULL, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | WS_TABSTOP | LVS_REPORT | LVS_AUTOARRANGE | LVS_SHOWSELALWAYS | LVS_SHAREIMAGELISTS/* | LVS_EDITLABELS*/, WS_EX_CLIENTEDGE,IDC_PROJECTLISTVIEW); m_ProjectListViewHeader.SubclassWindow(m_ProjectListView.GetHeader()); m_ProjectListViewContainer.SetClient(m_ProjectListView); m_ProjectListViewContainer.SetCustomDrawHandler(m_ProjectListView,IDC_PROJECTLISTVIEW); // Enable the extended list view styles. unsigned long ulLVExStyle = LVS_EX_HEADERDRAGDROP | LVS_EX_DOUBLEBUFFER | LVS_EX_FULLROWSELECT; /*if (g_GlobalSettings.m_bListGridLines) ulLVExStyle |= LVS_EX_GRIDLINES; if (g_GlobalSettings.m_bListTrackSel) ulLVExStyle |= LVS_EX_TRACKSELECT;*/ m_ProjectListView.SetExtendedListViewStyle(ulLVExStyle); // Create the list view menus. m_hProjListSelMenu = LoadMenu(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDR_PROJLISTSELMENU)); m_hProjListNoSelMenu = LoadMenu(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDR_PROJLISTNOSELMENU)); ATLVERIFY(NULL != m_ShellTreeMenu.LoadMenu(IDR_SHELLTREEMENU)); // Make the view style check items to radio items. CMenuItemInfo mii; mii.fMask = MIIM_FTYPE; mii.fType = MFT_RADIOCHECK; SetMenuItemInfo(m_hProjListNoSelMenu,ID_VIEW_LARGEICONS,FALSE,&mii); SetMenuItemInfo(m_hProjListNoSelMenu,ID_VIEW_SMALLICONS,FALSE,&mii); SetMenuItemInfo(m_hProjListNoSelMenu,ID_VIEW_LIST,FALSE,&mii); SetMenuItemInfo(m_hProjListNoSelMenu,ID_VIEW_DETAILS,FALSE,&mii); // Create the tree view container. m_ProjectTreeViewContainer.Create(m_ProjectView,rcDefault,NULL, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,WS_EX_CONTROLPARENT,(unsigned int)0,NULL); m_ProjectTreeViewContainer.SetHeaderHeight(m_ProjectListViewContainer.GetHeaderHeight()); m_ProjectTreeViewContainer.SetLabelText(lngGetString(TITLE_PROJECTVIEW)); // Create the tree view. m_ProjectTreeView.Create(m_ProjectTreeViewContainer,rcDefault,NULL, WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | WS_TABSTOP | TVS_HASLINES | TVS_HASBUTTONS | TVS_SHOWSELALWAYS | TVS_EDITLABELS, WS_EX_CLIENTEDGE,IDC_PROJECTTREEVIEW); m_ProjectTreeViewContainer.SetClient(m_ProjectTreeView); m_ProjectTreeViewContainer.SetCustomDrawHandler(m_ProjectTreeView,IDC_PROJECTTREEVIEW); InitializeProjectImageLists(); // Setup the view. m_ProjectView.SetSplitterPane(SPLIT_PANE_LEFT,m_ProjectTreeViewContainer); m_ProjectView.SetSplitterPane(SPLIT_PANE_RIGHT,m_ProjectListViewContainer); // Assign controls. g_TreeManager.AssignControls(&m_ProjectTreeView,&m_ProjectListView); g_ProjectManager.AssignControls(&m_ProjectView,&m_ProjectListViewContainer,&m_SpaceMeter,&m_ProjectListView,&m_ProjectTreeView); // Prepare the apropriate project type. int iDefaultMedia = GetDefaultMedia(); switch (m_iDefaultProjType) { case PROJECTTYPE_DATA: g_ProjectManager.NewDataProject(iDefaultMedia != -1 ? iDefaultMedia : SPACEMETER_SIZE_703MB); if (m_bDefaultProjDVDVideo) g_ProjectSettings.m_iFileSystem = FILESYSTEM_DVDVIDEO; break; case PROJECTTYPE_AUDIO: g_ProjectManager.NewAudioProject(iDefaultMedia != -1 ? iDefaultMedia : SPACEMETER_SIZE_80MIN); break; case PROJECTTYPE_MIXED: g_ProjectManager.NewMixedProject(iDefaultMedia != -1 ? iDefaultMedia : SPACEMETER_SIZE_703MB); break; } } void CMainFrame::InitializeProjectImageLists() { // Create the list view image list. SHFILEINFO shFileInfo = { 0 }; HIMAGELIST hImageListSmall = (HIMAGELIST)::SHGetFileInfo(_T(""), 0,&shFileInfo,sizeof(shFileInfo),SHGFI_ICON | SHGFI_SYSICONINDEX | SHGFI_SMALLICON); m_ProjectListView.SetImageList(hImageListSmall,LVSIL_SMALL); HIMAGELIST hImageListLarge = (HIMAGELIST)::SHGetFileInfo(_T(""), 0,&shFileInfo,sizeof(shFileInfo),SHGFI_ICON | SHGFI_SYSICONINDEX | SHGFI_ICON); m_ProjectListView.SetImageList(hImageListLarge,LVSIL_NORMAL); // Create the tree image list. m_hProjectTreeImageList = ImageList_Create(16,16,ILC_COLOR32,4,5); HICON hIcon; HINSTANCE hInstance = LoadLibrary(_T("shell32.dll")); hIcon = (HICON)LoadImage(hInstance,MAKEINTRESOURCE(4),IMAGE_ICON,16,16,/*LR_DEFAULTCOLOR*/LR_LOADTRANSPARENT); FreeLibrary(hInstance); ImageList_AddIcon(m_hProjectTreeImageList,hIcon); DestroyIcon(hIcon); hIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_DATAICON),IMAGE_ICON,16,16,LR_LOADTRANSPARENT); ImageList_AddIcon(m_hProjectTreeImageList,hIcon); DestroyIcon(hIcon); hIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_AUDIOICON),IMAGE_ICON,16,16,LR_LOADTRANSPARENT); ImageList_AddIcon(m_hProjectTreeImageList,hIcon); DestroyIcon(hIcon); hIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_MIXEDICON),IMAGE_ICON,16,16,LR_LOADTRANSPARENT); ImageList_AddIcon(m_hProjectTreeImageList,hIcon); DestroyIcon(hIcon); hIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_VIDEOICON),IMAGE_ICON,16,16,LR_LOADTRANSPARENT); ImageList_AddIcon(m_hProjectTreeImageList,hIcon); DestroyIcon(hIcon); m_ProjectTreeView.SetImageList(m_hProjectTreeImageList,LVSIL_NORMAL); } bool CMainFrame::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a main translation section. if (!pLng->EnterSection(_T("main"))) return false; // Sub menus. TCHAR *szStrValue; HMENU hMainMenu = m_CmdBar.GetMenu(); HMENU hCurMenu; if (pLng->GetValuePtr(ID_MENUROOT_FILE,szStrValue)) // File. { hCurMenu = ::GetSubMenu(hMainMenu,0); ::ModifyMenu(hMainMenu,0,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } if (pLng->GetValuePtr(ID_MENUROOT_EDIT,szStrValue)) // Edit. { hCurMenu = ::GetSubMenu(hMainMenu,1); ::ModifyMenu(hMainMenu,1,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } if (pLng->GetValuePtr(ID_MENUROOT_ACTIONS,szStrValue)) // Actions. { hCurMenu = ::GetSubMenu(hMainMenu,2); ::ModifyMenu(hMainMenu,2,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } if (pLng->GetValuePtr(ID_MENUROOT_VIEW,szStrValue)) // View. { hCurMenu = ::GetSubMenu(hMainMenu,3); ::ModifyMenu(hMainMenu,3,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); // Modify the popup menu. hCurMenu = GetSubMenu(m_hProjListNoSelMenu,0); HMENU hViewMenu = GetSubMenu(hCurMenu,0); ::ModifyMenu(hCurMenu,0,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hViewMenu,szStrValue); } if (pLng->GetValuePtr(ID_MENUROOT_OPTIONS,szStrValue)) // Options. { hCurMenu = ::GetSubMenu(hMainMenu,4); ::ModifyMenu(hMainMenu,4,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } if (pLng->GetValuePtr(ID_MENUROOT_HELP,szStrValue)) // Help. { hCurMenu = ::GetSubMenu(hMainMenu,5); ::ModifyMenu(hMainMenu,5,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } m_CmdBar.AttachMenu(hMainMenu); HMENU hSubMenu = GetSubMenu(hMainMenu,0); if (pLng->GetValuePtr(ID_FILE_NEWPROJECT,szStrValue)) // File -> New Project. { hCurMenu = ::GetSubMenu(hSubMenu,0); ::ModifyMenu(hSubMenu,0,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } hSubMenu = GetSubMenu(hMainMenu,1); if (pLng->GetValuePtr(ID_EDIT_ADDPROJECT,szStrValue)) // Edit -> Add. { hCurMenu = ::GetSubMenu(hSubMenu,3); ::ModifyMenu(hSubMenu,3,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } hSubMenu = GetSubMenu(hMainMenu,2); if (pLng->GetValuePtr(ID_ACTIONS_BURNCOMPILATION,szStrValue)) // Actions -> Burn Compilation. { hCurMenu = ::GetSubMenu(hSubMenu,0); ::ModifyMenu(hSubMenu,0,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } if (pLng->GetValuePtr(ID_ACTIONS_COPYDISC,szStrValue)) // Actions -> Copy Disc. { hCurMenu = ::GetSubMenu(hSubMenu,2); ::ModifyMenu(hSubMenu,2,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } if (pLng->GetValuePtr(ID_ACTIONS_DISCINFORMATION,szStrValue)) { hCurMenu = ::GetSubMenu(hSubMenu,MENU_DISCINFO_INDEX); ::ModifyMenu(hSubMenu,MENU_DISCINFO_INDEX,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } if (pLng->GetValuePtr(ID_ACTIONS_EJECT,szStrValue)) // Actions -> Eject Disc. { hCurMenu = ::GetSubMenu(hSubMenu,MENU_EJECTDISC_INDEX); ::ModifyMenu(hSubMenu,MENU_EJECTDISC_INDEX,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } hSubMenu = GetSubMenu(hMainMenu,3); if (pLng->GetValuePtr(ID_VIEW_TOOLBARS,szStrValue)) // View -> Toolbars. { hCurMenu = ::GetSubMenu(hSubMenu,0); ::ModifyMenu(hSubMenu,0,MF_POPUP | MF_BYPOSITION | MF_STRING,(UINT_PTR)hCurMenu,szStrValue); } // File menu. hCurMenu = GetSubMenu(hMainMenu,0); if (pLng->GetValuePtr(ID_FILE_OPEN,szStrValue)) { TCHAR szMenuString[64]; lstrncpy(szMenuString,szStrValue,sizeof(szMenuString) / sizeof(TCHAR) - 8); lstrcat(szMenuString,_T("\tCtrl+O")); ModifyMenu(hCurMenu,ID_FILE_OPEN,MF_BYCOMMAND | MF_STRING,ID_FILE_OPEN,(LPCTSTR)szMenuString); } if (pLng->GetValuePtr(ID_FILE_SAVE,szStrValue)) { TCHAR szMenuString[64]; lstrncpy(szMenuString,szStrValue,sizeof(szMenuString) / sizeof(TCHAR) - 8); lstrcat(szMenuString,_T("\tCtrl+S")); ModifyMenu(hCurMenu,ID_FILE_SAVE,MF_BYCOMMAND | MF_STRING,ID_FILE_SAVE,(LPCTSTR)szMenuString); } if (pLng->GetValuePtr(ID_FILE_SAVE_AS,szStrValue)) ModifyMenu(hCurMenu,ID_FILE_SAVE_AS,MF_BYCOMMAND | MF_STRING,ID_FILE_SAVE_AS,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_FILE_PROJECTPROPERTIES,szStrValue)) ModifyMenu(hCurMenu,ID_FILE_PROJECTPROPERTIES,MF_BYCOMMAND | MF_STRING,ID_FILE_PROJECTPROPERTIES,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_APP_EXIT,szStrValue)) ModifyMenu(hCurMenu,ID_APP_EXIT,MF_BYCOMMAND | MF_STRING,ID_APP_EXIT,(LPCTSTR)szStrValue); // New project menu. hCurMenu = GetSubMenu(hCurMenu,0); if (pLng->GetValuePtr(ID_NEWPROJECT_DATACD,szStrValue)) ModifyMenu(hCurMenu,ID_NEWPROJECT_DATACD,MF_BYCOMMAND | MF_STRING,ID_NEWPROJECT_DATACD,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_NEWPROJECT_DATACDMS,szStrValue)) ModifyMenu(hCurMenu,ID_NEWPROJECT_DATACDMS,MF_BYCOMMAND | MF_STRING,ID_NEWPROJECT_DATACDMS,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_NEWPROJECT_AUDIO,szStrValue)) ModifyMenu(hCurMenu,ID_NEWPROJECT_AUDIO,MF_BYCOMMAND | MF_STRING,ID_NEWPROJECT_AUDIO,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_NEWPROJECT_MIXED,szStrValue)) ModifyMenu(hCurMenu,ID_NEWPROJECT_MIXED,MF_BYCOMMAND | MF_STRING,ID_NEWPROJECT_MIXED,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_NEWPROJECT_DVDVIDEO,szStrValue)) ModifyMenu(hCurMenu,ID_NEWPROJECT_DVDVIDEO,MF_BYCOMMAND | MF_STRING,ID_NEWPROJECT_DVDVIDEO,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_NEWPROJECT_DATADVD,szStrValue)) ModifyMenu(hCurMenu,ID_NEWPROJECT_DATADVD,MF_BYCOMMAND | MF_STRING,ID_NEWPROJECT_DATADVD,(LPCTSTR)szStrValue); // Edit menu. hCurMenu = GetSubMenu(hMainMenu,1); if (pLng->GetValuePtr(ID_EDIT_NEWFOLDER,szStrValue)) { ModifyMenu(hCurMenu,ID_EDIT_NEWFOLDER,MF_BYCOMMAND | MF_STRING,ID_EDIT_NEWFOLDER,(LPCTSTR)szStrValue); // Modify the popup menu. ModifyMenu(m_hProjListNoSelMenu,ID_EDIT_NEWFOLDER,MF_BYCOMMAND | MF_STRING,ID_EDIT_NEWFOLDER,(LPCTSTR)szStrValue); } if (pLng->GetValuePtr(ID_EDIT_RENAME,szStrValue)) { TCHAR szMenuString[64]; lstrncpy(szMenuString,szStrValue,sizeof(szMenuString) / sizeof(TCHAR) - 4); lstrcat(szMenuString,_T("\tF2")); ModifyMenu(hCurMenu,ID_EDIT_RENAME,MF_BYCOMMAND | MF_STRING,ID_EDIT_RENAME,(LPCTSTR)szMenuString); // Modify the popup menu. ModifyMenu(m_hProjListSelMenu,ID_EDIT_RENAME,MF_BYCOMMAND | MF_STRING,ID_EDIT_RENAME,(LPCTSTR)szStrValue); } if (pLng->GetValuePtr(ID_EDIT_REMOVE,szStrValue)) { TCHAR szMenuString[64]; lstrncpy(szMenuString,szStrValue,sizeof(szMenuString) / sizeof(TCHAR) - 5); lstrcat(szMenuString,_T("\tDel")); ModifyMenu(hCurMenu,ID_EDIT_REMOVE,MF_BYCOMMAND | MF_STRING,ID_EDIT_REMOVE,(LPCTSTR)szMenuString); // Modify the popup menu. ModifyMenu(m_hProjListSelMenu,ID_EDIT_REMOVE,MF_BYCOMMAND | MF_STRING,ID_EDIT_REMOVE,(LPCTSTR)szStrValue); } if (pLng->GetValuePtr(ID_EDIT_IMPORT,szStrValue)) ModifyMenu(hCurMenu,ID_EDIT_IMPORT,MF_BYCOMMAND | MF_STRING,ID_EDIT_IMPORT,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_EDIT_SELECTALL,szStrValue)) { TCHAR szMenuString[64]; lstrncpy(szMenuString,szStrValue,sizeof(szMenuString) / sizeof(TCHAR) - 8); lstrcat(szMenuString,_T("\tCtrl+A")); ModifyMenu(hCurMenu,ID_EDIT_SELECTALL,MF_BYCOMMAND | MF_STRING,ID_EDIT_SELECTALL,(LPCTSTR)szMenuString); } if (pLng->GetValuePtr(ID_EDIT_INVERTSELECTION,szStrValue)) ModifyMenu(hCurMenu,ID_EDIT_INVERTSELECTION,MF_BYCOMMAND | MF_STRING,ID_EDIT_INVERTSELECTION,(LPCTSTR)szStrValue); // Add menu. hCurMenu = GetSubMenu(hCurMenu,3); if (pLng->GetValuePtr(ID_ADD_SELECTED,szStrValue)) ModifyMenu(hCurMenu,ID_ADD_SELECTED,MF_BYCOMMAND | MF_STRING,ID_ADD_SELECTED,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_ADD_ALL,szStrValue)) ModifyMenu(hCurMenu,ID_ADD_ALL,MF_BYCOMMAND | MF_STRING,ID_ADD_ALL,(LPCTSTR)szStrValue); // Actions menu. hCurMenu = GetSubMenu(hMainMenu,2); if (pLng->GetValuePtr(ID_ACTIONS_BURNIMAGE,szStrValue)) ModifyMenu(hCurMenu,ID_ACTIONS_BURNIMAGE,MF_BYCOMMAND | MF_STRING,ID_ACTIONS_BURNIMAGE,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_ACTIONS_MANAGETRACKS,szStrValue)) ModifyMenu(hCurMenu,ID_ACTIONS_MANAGETRACKS,MF_BYCOMMAND | MF_STRING,ID_ACTIONS_MANAGETRACKS,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_ACTIONS_ERASERE,szStrValue)) ModifyMenu(hCurMenu,ID_ACTIONS_ERASERE,MF_BYCOMMAND | MF_STRING,ID_ACTIONS_ERASERE,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_ACTIONS_FIXATEDISC,szStrValue)) ModifyMenu(hCurMenu,ID_ACTIONS_FIXATEDISC,MF_BYCOMMAND | MF_STRING,ID_ACTIONS_FIXATEDISC,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_ACTIONS_IMPORTSESSION,szStrValue)) ModifyMenu(hCurMenu,ID_ACTIONS_IMPORTSESSION,MF_BYCOMMAND | MF_STRING,ID_ACTIONS_IMPORTSESSION,(LPCTSTR)szStrValue); // Burn compilation menu. hCurMenu = GetSubMenu(hCurMenu,0); if (pLng->GetValuePtr(ID_BURNCOMPILATION_DISCIMAGE,szStrValue)) ModifyMenu(hCurMenu,ID_BURNCOMPILATION_DISCIMAGE,MF_BYCOMMAND | MF_STRING,ID_BURNCOMPILATION_DISCIMAGE,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_BURNCOMPILATION_COMPACTDISC,szStrValue)) ModifyMenu(hCurMenu,ID_BURNCOMPILATION_COMPACTDISC,MF_BYCOMMAND | MF_STRING,ID_BURNCOMPILATION_COMPACTDISC,(LPCTSTR)szStrValue); // Copy disc menu (same strings as compilation menu). hCurMenu = GetSubMenu(GetSubMenu(hMainMenu,2),2); if (pLng->GetValuePtr(ID_BURNCOMPILATION_DISCIMAGE,szStrValue)) ModifyMenu(hCurMenu,ID_COPYDISC_DISCIMAGE,MF_BYCOMMAND | MF_STRING,ID_COPYDISC_DISCIMAGE,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_BURNCOMPILATION_COMPACTDISC,szStrValue)) ModifyMenu(hCurMenu,ID_COPYDISC_COMPACTDISC,MF_BYCOMMAND | MF_STRING,ID_COPYDISC_COMPACTDISC,(LPCTSTR)szStrValue); // View menu. hCurMenu = GetSubMenu(hMainMenu,3); if (pLng->GetValuePtr(ID_VIEW_STATUS_BAR,szStrValue)) ModifyMenu(hCurMenu,ID_VIEW_STATUS_BAR,MF_BYCOMMAND | MF_STRING,ID_VIEW_STATUS_BAR,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_VIEW_PROGRAMLOG,szStrValue)) ModifyMenu(hCurMenu,ID_VIEW_PROGRAMLOG,MF_BYCOMMAND | MF_STRING,ID_VIEW_PROGRAMLOG,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_VIEW_LARGEICONS,szStrValue)) { ModifyMenu(hCurMenu,ID_VIEW_LARGEICONS,MF_BYCOMMAND | MF_STRING,ID_VIEW_LARGEICONS,(LPCTSTR)szStrValue); // Modify the popup menu. ModifyMenu(GetSubMenu(m_hProjListNoSelMenu,0),ID_VIEW_LARGEICONS,MF_BYCOMMAND | MF_STRING,ID_VIEW_LARGEICONS,(LPCTSTR)szStrValue); } if (pLng->GetValuePtr(ID_VIEW_SMALLICONS,szStrValue)) { ModifyMenu(hCurMenu,ID_VIEW_SMALLICONS,MF_BYCOMMAND | MF_STRING,ID_VIEW_SMALLICONS,(LPCTSTR)szStrValue); // Modify the popup menu. ModifyMenu(GetSubMenu(m_hProjListNoSelMenu,0),ID_VIEW_SMALLICONS,MF_BYCOMMAND | MF_STRING,ID_VIEW_SMALLICONS,(LPCTSTR)szStrValue); } if (pLng->GetValuePtr(ID_VIEW_LIST,szStrValue)) { ModifyMenu(hCurMenu,ID_VIEW_LIST,MF_BYCOMMAND | MF_STRING,ID_VIEW_LIST,(LPCTSTR)szStrValue); // Modify the popup menu. ModifyMenu(GetSubMenu(m_hProjListNoSelMenu,0),ID_VIEW_LIST,MF_BYCOMMAND | MF_STRING,ID_VIEW_LIST,(LPCTSTR)szStrValue); } if (pLng->GetValuePtr(ID_VIEW_DETAILS,szStrValue)) { ModifyMenu(hCurMenu,ID_VIEW_DETAILS,MF_BYCOMMAND | MF_STRING,ID_VIEW_DETAILS,(LPCTSTR)szStrValue); // Modify the popup menu. ModifyMenu(GetSubMenu(m_hProjListNoSelMenu,0),ID_VIEW_DETAILS,MF_BYCOMMAND | MF_STRING,ID_VIEW_DETAILS,(LPCTSTR)szStrValue); } // Toolbars menu. hCurMenu = GetSubMenu(hCurMenu,0); if (pLng->GetValuePtr(ID_VIEW_STANDARDTOOLBAR,szStrValue)) ModifyMenu(hCurMenu,ID_VIEW_STANDARDTOOLBAR,MF_BYCOMMAND | MF_STRING,ID_VIEW_STANDARDTOOLBAR,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_VIEW_TBCUSTOMIZE,szStrValue)) ModifyMenu(hCurMenu,ID_VIEW_TBCUSTOMIZE,MF_BYCOMMAND | MF_STRING,ID_VIEW_TBCUSTOMIZE,(LPCTSTR)szStrValue); // Options menu. hCurMenu = GetSubMenu(hMainMenu,4); if (pLng->GetValuePtr(ID_OPTIONS_CONFIGURATION,szStrValue)) ModifyMenu(hCurMenu,ID_OPTIONS_CONFIGURATION,MF_BYCOMMAND | MF_STRING,ID_OPTIONS_CONFIGURATION,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_OPTIONS_DEVICES,szStrValue)) ModifyMenu(hCurMenu,ID_OPTIONS_DEVICES,MF_BYCOMMAND | MF_STRING,ID_OPTIONS_DEVICES,(LPCTSTR)szStrValue); // Help menu. hCurMenu = GetSubMenu(hMainMenu,5); if (pLng->GetValuePtr(ID_HELP_HELPTOPICS,szStrValue)) ModifyMenu(hCurMenu,ID_HELP_HELPTOPICS,MF_BYCOMMAND | MF_STRING,ID_HELP_HELPTOPICS,(LPCTSTR)szStrValue); if (pLng->GetValuePtr(ID_APP_ABOUT,szStrValue)) { TCHAR szTitle[32]; ::LoadString(_Module.GetResourceInstance(),IDR_MAINFRAME,szTitle,32); TCHAR szBuffer[64]; lstrcpy(szBuffer,szStrValue); lstrcat(szBuffer,_T(" ")); lstrcat(szBuffer,szTitle); lstrcat(szBuffer,_T("...")); ModifyMenu(hCurMenu,ID_APP_ABOUT,MF_BYCOMMAND | MF_STRING,ID_APP_ABOUT,(LPCTSTR)szBuffer); } // Project list seleced menu. if (pLng->GetValuePtr(ID_POPUPMENU_PROPERTIES,szStrValue)) { ModifyMenu(m_hProjListSelMenu,ID_POPUPMENU_PROPERTIES,MF_BYCOMMAND | MF_STRING, ID_POPUPMENU_PROPERTIES,(LPCTSTR)szStrValue); } return true; } void CMainFrame::FillDriveMenus() { // Update the menu. HMENU hActionsMenu = GetSubMenu(m_CmdBar.GetMenu(),MENU_ACTIONS_INDEX); HMENU hDiscMenu = GetSubMenu(hActionsMenu,MENU_DISCINFO_INDEX); HMENU hEjectMenu = GetSubMenu(hActionsMenu,MENU_EJECTDISC_INDEX); // Remove the old items. int iMenuItemCount = GetMenuItemCount(hEjectMenu); int iMenuIndex = 0; for (int i = iMenuItemCount - 1; i >= 0; i--) { RemoveMenu(hDiscMenu,i,MF_BYPOSITION); RemoveMenu(hEjectMenu,i,MF_BYPOSITION); } if (g_DeviceManager.devices().size() > 0) { std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; ckcore::tstring DeviceName = NDeviceUtil::GetDeviceName(*pDevice); AppendMenu(hDiscMenu,MF_STRING,MENU_DISCINFO_IDBASE + iMenuIndex,DeviceName.c_str()); AppendMenu(hEjectMenu,MF_STRING,MENU_EJECTDISC_IDBASE + iMenuIndex,DeviceName.c_str()); m_DriveMenuDeviceMap[iMenuIndex] = pDevice; // Increase the menu index counter. iMenuIndex++; } } else { AppendMenu(hDiscMenu,MF_STRING,0,lngGetString(EJECTMENU_NODRIVES)); AppendMenu(hEjectMenu,MF_STRING,0,lngGetString(EJECTMENU_NODRIVES)); CMenuItemInfo mii; mii.fMask = MIIM_STATE; mii.fState = MFS_GRAYED; SetMenuItemInfo(hEjectMenu,0,TRUE,&mii); } } void CMainFrame::SetTitleFile(const TCHAR *szFullName) { // Update the title. TCHAR szTitle[MAX_PATH + 32]; ::LoadString(_Module.GetResourceInstance(),IDR_MAINFRAME,szTitle,32); lstrcat(szTitle,_T(" - ")); TCHAR szFileName[MAX_PATH]; lstrcpy(szFileName,szFullName); ExtractFileName(szFileName); lstrcat(szTitle,szFileName); SetWindowText(szTitle); } void CMainFrame::SetTitleNormal() { // Update the title. TCHAR szTitle[32]; ::LoadString(_Module.GetResourceInstance(),IDR_MAINFRAME,szTitle,32); SetWindowText(szTitle); } bool CMainFrame::SaveProjectAs() { WTL::CFileDialog FileDialog(false,_T("irp"),_T("Untitled"),OFN_EXPLORER | OFN_OVERWRITEPROMPT, _T("Project Files (*.irp)\0*.irp\0\0"),m_hWnd); if (FileDialog.DoModal() == IDOK) { CWaitCursor WaitCursor; // This displays the hourglass cursor. lstrcpy(m_szProjectFile,FileDialog.m_szFileName); // Save the project. g_ProjectManager.SaveProject(m_szProjectFile); // Update the title. SetTitleFile(m_szProjectFile); return true; } return false; } /* CMainFrame::SaveProjectPrompt ----------------------------- Asks the user to if the project should be saved if it has been modified. The function returns false if the operation was aborted, otherwise true. */ bool CMainFrame::SaveProjectPrompt() { if (g_ProjectManager.GetModified()) { switch (lngMessageBox(m_hWnd,CONFIRM_SAVEPROJECT,GENERAL_QUESTION,MB_YESNOCANCEL | MB_ICONQUESTION)) { case IDYES: if (m_szProjectFile[0] == '\0') if (!SaveProjectAs()) return false; else { CWaitCursor WaitCursor; // This displays the hourglass cursor. g_ProjectManager.SaveProject(m_szProjectFile); } break; case IDCANCEL: return false; }; } return true; } LRESULT CMainFrame::OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Main small image list (menus and small toolbar buttons). InitializeMainSmallImageList(); // Create command bar window. HWND hWndCmdBar = m_CmdBar.Create(m_hWnd,rcDefault,NULL,ATL_SIMPLE_CMDBAR_PANE_STYLE); m_CmdBar.AttachMenu(GetMenu()); m_CmdBar.m_hImageList = m_hMainSmallImageList; // Set the menu items image index. m_CmdBar.m_arrCommand.Add(ID_FILE_OPEN); m_CmdBar.m_arrCommand.Add(ID_FILE_SAVE); m_CmdBar.m_arrCommand.Add(ID_FILE_SAVE_AS); m_CmdBar.m_arrCommand.Add(ID_FILE_PROJECTPROPERTIES); m_CmdBar.m_arrCommand.Add(ID_APP_EXIT); m_CmdBar.m_arrCommand.Add(ID_EDIT_NEWFOLDER); m_CmdBar.m_arrCommand.Add(ID_EDIT_RENAME); m_CmdBar.m_arrCommand.Add(ID_EDIT_REMOVE); m_CmdBar.m_arrCommand.Add(ID_ACTIONS_BURNCOMPILATION); // Not visible. m_CmdBar.m_arrCommand.Add(ID_ACTIONS_BURNIMAGE); m_CmdBar.m_arrCommand.Add(ID_ACTIONS_COPYDISC); // Not visible. m_CmdBar.m_arrCommand.Add(ID_ACTIONS_MANAGETRACKS); m_CmdBar.m_arrCommand.Add(ID_ACTIONS_ERASERE); m_CmdBar.m_arrCommand.Add(ID_ACTIONS_FIXATEDISC); m_CmdBar.m_arrCommand.Add(ID_VIEW_PROGRAMLOG); m_CmdBar.m_arrCommand.Add(ID_OPTIONS_CONFIGURATION); m_CmdBar.m_arrCommand.Add(ID_OPTIONS_DEVICES); m_CmdBar.m_arrCommand.Add(ID_HELP_HELPTOPICS); m_CmdBar.m_arrCommand.Add(ID_APP_ABOUT); // Remove old menu. SetMenu(NULL); HWND hWndToolBar = CreateToolBarCtrl(); CreateSimpleReBar(ATL_SIMPLE_REBAR_NOBORDER_STYLE); AddSimpleReBarBandCtrl(m_hWndToolBar,hWndCmdBar,REBAR_MENUBAR_ID,NULL,true,0,FALSE); AddSimpleReBarBandCtrl(m_hWndToolBar,hWndToolBar,REBAR_TOOLBAR_ID,NULL,true,0,FALSE); CreateSimpleStatusBar(); UIAddToolBar(hWndToolBar); UISetCheck(ID_VIEW_STANDARDTOOLBAR,1); UISetCheck(ID_VIEW_STATUS_BAR,1); // Register object for message filtering and idle updates. CMessageLoop *pLoop = _Module.GetMessageLoop(); ATLASSERT(pLoop != NULL); pLoop->AddMessageFilter(this); pLoop->AddIdleHandler(this); // Make the view style check items to radio items. CMenuItemInfo mii; mii.fMask = MIIM_FTYPE; mii.fType = MFT_RADIOCHECK; SetMenuItemInfo(m_hProjListNoSelMenu,ID_VIEW_LARGEICONS,FALSE,&mii); SetMenuItemInfo(m_hProjListNoSelMenu,ID_VIEW_SMALLICONS,FALSE,&mii); SetMenuItemInfo(m_hProjListNoSelMenu,ID_VIEW_LIST,FALSE,&mii); SetMenuItemInfo(m_hProjListNoSelMenu,ID_VIEW_DETAILS,FALSE,&mii); // Mini tool bar image list. InitializeMiniToolBarImageList(); // Initialize views. RECT rcClient; GetClientRect(&rcClient); int iSplitterPos = (rcClient.right - rcClient.left) / 4; InitializeMainView(); InitializeExplorerView(iSplitterPos); bool bWelcomePane = false; if (bWelcomePane) m_SpaceMeterView.SetSinglePaneMode(SPLIT_PANE_TOP); else InitializeProjectView(iSplitterPos); // Perform an autorun check. //if (g_GlobalSettings.m_bAutoRunCheck) // AutoRunCheck(); // WARNING: The auto run check has been experimentally replaced by temporarily // disabling the auto run while InfraRecorder is running. m_bEnableAutoRun = EnableAutoRun(false); // Fill drive menus. FillDriveMenus(); // Apply the settings. if (!bWelcomePane) g_DynamicSettings.Apply(); // Show/hide the tool bar and status bar. if (!g_DynamicSettings.m_bViewToolBar) { UISetCheck(ID_VIEW_STANDARDTOOLBAR,0); UpdateLayout(); ::SendMessage(m_hWndToolBar,RB_SHOWBAND, ::SendMessage(m_hWndToolBar,RB_IDTOINDEX,REBAR_TOOLBAR_ID,0),false); } if (!g_DynamicSettings.m_bViewStatusBar) { UISetCheck(ID_VIEW_STATUS_BAR,0); UpdateLayout(); ::ShowWindow(m_hWndStatusBar,SW_HIDE); } // Initialize drag and drop. ATLVERIFY(SUCCEEDED(RegisterDragDrop(m_ProjectTreeView,m_ProjectTreeView.m_pDropTarget))); ATLVERIFY(SUCCEEDED(RegisterDragDrop(m_ProjectListView,m_ProjectListView.m_pDropTarget))); // Translate the window. Translate(); if (m_szProjectFile[0] != '\0') { CWaitCursor WaitCursor; // This displays the hourglass cursor. if (g_ProjectManager.LoadProject(m_szProjectFile)) { // Update the view. g_TreeManager.Refresh(); SetTitleFile(m_szProjectFile); } } // Confirm buffer. TCHAR szBuffer[32]; ::LoadString(_Module.GetResourceInstance(),128,szBuffer,32); size_t iBufferLen = lstrlen(szBuffer); for (size_t i = 0; i < iBufferLen; i++) szBuffer[i] = szBuffer[i] ^ 0xFF; TCHAR szTarget[] = { 0x49^0xFF,0x6E^0xFF,0x66^0xFF,0x72^0xFF,0x61^0xFF, 0x52^0xFF,0x65^0xFF,0x63^0xFF,0x6F^0xFF,0x72^0xFF, 0x64^0xFF,0x65^0xFF,0x72^0xFF,'\0' }; if (lstrcmp(szTarget,szBuffer)) { TCHAR szBuffer[] = { 0x59^0xFF,0x6F^0xFF,0x75^0xFF,0x72^0xFF,0x20^0xFF, 0x76^0xFF,0x65^0xFF,0x72^0xFF,0x73^0xFF,0x69^0xFF,0x6F^0xFF,0x6E^0xFF, 0x20^0xFF,0x6F^0xFF,0x66^0xFF,0x20^0xFF,0x49^0xFF,0x6E^0xFF,0x66^0xFF, 0x72^0xFF,0x61^0xFF,0x52^0xFF,0x65^0xFF,0x63^0xFF,0x6F^0xFF,0x72^0xFF, 0x64^0xFF,0x65^0xFF,0x72^0xFF,0x20^0xFF,0x68^0xFF,0x61^0xFF,0x73^0xFF, 0x20^0xFF,0x62^0xFF,0x65^0xFF,0x65^0xFF,0x6E^0xFF,0x20^0xFF,0x61^0xFF, 0x6C^0xFF,0x74^0xFF,0x65^0xFF,0x72^0xFF,0x65^0xFF,0x64^0xFF,0x2C^0xFF, 0x20^0xFF,0x70^0xFF,0x6C^0xFF,0x65^0xFF,0x61^0xFF,0x73^0xFF,0x65^0xFF, 0x20^0xFF,0x6D^0xFF,0x61^0xFF,0x6B^0xFF,0x65^0xFF,0x20^0xFF,0x73^0xFF, 0x75^0xFF,0x72^0xFF,0x65^0xFF,0x20^0xFF,0x74^0xFF,0x68^0xFF,0x61^0xFF, 0x74^0xFF,0x20^0xFF,0x79^0xFF,0x6F^0xFF,0x75^0xFF,0x20^0xFF,0x68^0xFF, 0x61^0xFF,0x76^0xFF,0x65^0xFF,0x20^0xFF,0x64^0xFF,0x6F^0xFF,0x77^0xFF, 0x6E^0xFF,0x6C^0xFF,0x6F^0xFF,0x61^0xFF,0x64^0xFF,0x65^0xFF,0x64^0xFF, 0x20^0xFF,0x79^0xFF,0x6F^0xFF,0x75^0xFF,0x72^0xFF,0x20^0xFF,0x76^0xFF, 0x65^0xFF,0x72^0xFF,0x73^0xFF,0x69^0xFF,0x6F^0xFF,0x6E^0xFF,0x20^0xFF, 0x66^0xFF,0x72^0xFF,0x6F^0xFF,0x6D^0xFF,0x20^0xFF,0x68^0xFF,0x74^0xFF, 0x74^0xFF,0x70^0xFF,0x3A^0xFF,0x2F^0xFF,0x2F^0xFF,0x69^0xFF,0x6E^0xFF, 0x66^0xFF,0x72^0xFF,0x61^0xFF,0x72^0xFF,0x65^0xFF,0x63^0xFF,0x6F^0xFF, 0x72^0xFF,0x64^0xFF,0x65^0xFF,0x72^0xFF,0x2E^0xFF,0x6F^0xFF,0x72^0xFF, 0x67^0xFF,'\0' }; size_t iBufferLen = lstrlen(szBuffer); for (size_t i = 0; i < iBufferLen; i++) szBuffer[i] = szBuffer[i] ^ 0xFF; MessageBox(szBuffer,_T(""),MB_OK | MB_ICONWARNING); } return 0; } HMENU CMainFrame::GetToolBarsMenu() { // Just divided the different sections up a bit so it's easier to see. HMENU hViewMenu = GetSubMenu(m_CmdBar.GetMenu(),MENU_VIEW_INDEX); HMENU hToolBarsMenu = GetSubMenu(hViewMenu,MENU_TOOLBARS_INDEX); return hToolBarsMenu; } HIMAGELIST CMainFrame::GetToolBarSmall() { return m_hMainSmallImageList; } HIMAGELIST CMainFrame::GetToolBarLarge() { return m_hMainLargeImageList; } LRESULT CMainFrame::OnDestroy(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // If auto run was enabled before InfraRecorder was started, re-enable it. if (m_bEnableAutoRun) EnableAutoRun(true); // Uninitialize the shell list view drag and drop. ATLVERIFY(SUCCEEDED(RevokeDragDrop(m_ProjectListView))); ATLVERIFY(SUCCEEDED(RevokeDragDrop(m_ProjectTreeView))); // Save the configuration. g_SettingsManager.Save(); // Destroy the m_pShellView object. if (m_pShellListView != NULL) { m_ShellListViewContainer.SetClient(NULL); delete m_pShellListView; } // Deregister the directory monitor. m_DirectoryMonitor.Deregister(); // Destroy project tree view image list. if (m_hProjectTreeImageList) ImageList_Destroy(m_hProjectTreeImageList); // Destroy the project list view menus. DestroyMenu(m_hProjListSelMenu); DestroyMenu(m_hProjListNoSelMenu); // Destroy the mini tool bar image list. if (m_hMiniToolBarImageList) ImageList_Destroy(m_hMiniToolBarImageList); // Destroy the main small image list. if (m_hMainSmallImageList) ImageList_Destroy(m_hMainSmallImageList); // If we don't call PostQuitMessage() ourselves, // CFrameWindowImplBase::OnDestroy() will do it for us, // but then the application will end with exit code 1, // and applications which terminate normally should // actually end with exit code 0. ATLASSERT(bHandled); // Should have been set by WTL. PostQuitMessage(0); return 0; } LRESULT CMainFrame::OnClose(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // FIXME: Add a check to see if the project is empty here. It's no idea to promt // to save if the project is empty. if (!SaveProjectPrompt()) { bHandled = true; return TRUE; } // Remember the current window position and size. if (IsWindowVisible() && !IsIconic() && !IsZoomed() && !m_bWelcomePane) GetWindowRect(&g_DynamicSettings.m_rcWindow); g_DynamicSettings.m_bWinMaximized = IsZoomed() == TRUE; bHandled = false; return 0; } LRESULT CMainFrame::OnShellChange(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // This message is send completeley asynchronous. This will case a problem, // especially since the Windows Shell seems to send a couple identical messages // every time. For example: If the AddFolder routine has begin its execution and // it has checked so no other identical items exsists, it can be interupted by // a new message. This will cause duplicate folders to be added. // This problem is solved by ignoring all shell change notificiation while // processing one. static bool bLocked = false; if (!bLocked) bLocked = true; else return 0; LPITEMIDLIST *ppidls = reinterpret_cast(wParam); static bool bPhase = true; TCHAR szPath[MAX_PATH]; switch (lParam) { // A directory was created. case SHCNE_MKDIR: m_PidlHelp.GetPathName(ppidls[0],szPath); AddFolder(szPath); break; // A folder was renamed. case SHCNE_RENAMEFOLDER: RenameFolder(ppidls[0],ppidls[1]); break; // A folder was removed. case SHCNE_RMDIR: RemoveFolder(ppidls[0]); break; } bLocked = false; return 0; } LRESULT CMainFrame::OnGetIShellBrowser(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // This is very important, we need to redirect this message to the main frame that can return // the correct IShellBrowser object. If we do not answer to this message the CreateViewObject // function call will fail on Windows 98 systems for all other directories than the desktop. bHandled = TRUE; return (LRESULT)m_pShellListView; } LRESULT CMainFrame::OnContextMenu(UINT uMsg,WPARAM wParam,LPARAM lParam, BOOL &bHandled) { try { ATLASSERT(uMsg == WM_CONTEXTMENU); // At this point WM_CONTEXTMENU comes normally from the m_SpaceMeterView window, // which I don't really understand. // // In the case of the shell tree, our implementation of OnSTVRClick() // calls this routine directly with the right window handle. // // If the user calls up the context menu with the keyboard (with Shift+F10 // or the context-menu key on modern keyboards), we still get the // m_SpaceMeterView window handle, so we need handle this case as an exception. POINT ptPos; ptPos.x = GET_X_LPARAM(lParam); ptPos.y = GET_Y_LPARAM(lParam); const bool bWasWithKeyboard = (ptPos.x == -1) && (ptPos.y == -1); if (bWasWithKeyboard) { // I couldn't think of anything better than the focus // in order to find out whether the user was on the shell tree. if (GetFocus() == m_ShellTreeView.m_hWnd) { DisplayContextMenuOnShellTree(ptPos,bWasWithKeyboard); bHandled = TRUE; return 0; } // FIXME: I've noticed that the project tree does not respond // to Shift+F10, this would be the place to fix it. } else { if (HWND(wParam) == m_ShellTreeView.m_hWnd) { DisplayContextMenuOnShellTree(ptPos,bWasWithKeyboard); bHandled = TRUE; return 0; } } // At this point, we are not handling this WM_CONTEXTMENU message, // but somebody else probably will. } catch (const std::exception &e) { // After displaying the error message box, this message // should probably not be processed any further. bHandled = TRUE; ATLVERIFY(IDOK == MessageBox(ckcore::get_except_msg(e).c_str(), lngGetString(GENERAL_ERROR), MB_OK | MB_ICONERROR)); } return 0; } LRESULT CMainFrame::OnDeviceChange(UINT uMsg,WPARAM wParam,LPARAM lParam, BOOL &bHandled) { PDEV_BROADCAST_HDR lpdb = (PDEV_BROADCAST_HDR)lParam; if (wParam == DBT_DEVICEARRIVAL && lpdb->dbch_devicetype == DBT_DEVTYP_VOLUME) { PDEV_BROADCAST_VOLUME lpdbv = (PDEV_BROADCAST_VOLUME)lpdb; if (lpdbv->dbcv_flags & DBTF_MEDIA) { bHandled = TRUE; // Find which recorder that the media was changed for. std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { ckmmc::Device *pDevice = *it; int iDevLetterNum = toupper(pDevice->address().device_[0]) - 'A'; bool bDevHadMediaChange = (lpdbv->dbcv_unitmask & (1 << iDevLetterNum)) > 0; // Check if the current device was affected. if (pDevice->recorder() && bDevHadMediaChange) { CCore2Info Info; CCore2DiscInfo DiscInfo; // Fetch media information. if (Info.ReadDiscInformation(*pDevice,&DiscInfo) && DiscInfo.m_ucDiscStatus == CCore2DiscInfo::DS_EMTPY) { switch (pDevice->profile()) { case ckmmc::Device::ckPROFILE_DVDRAM: case ckmmc::Device::ckPROFILE_DVDPLUSRW: case ckmmc::Device::ckPROFILE_DVDMINUSRW_RESTOV: case ckmmc::Device::ckPROFILE_DVDMINUSRW_SEQ: case ckmmc::Device::ckPROFILE_DVDMINUSR_SEQ: case ckmmc::Device::ckPROFILE_DVDPLUSR: m_SpaceMeter.SetDiscSize(SPACEMETER_SIZE_DVD); m_SpaceMeter.Invalidate(); break; case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_SEQ: case ckmmc::Device::ckPROFILE_DVDMINUSR_DL_JUMP: case ckmmc::Device::ckPROFILE_DVDPLUSRW_DL: case ckmmc::Device::ckPROFILE_DVDPLUSR_DL: m_SpaceMeter.SetDiscSize(SPACEMETER_SIZE_DLDVD); m_SpaceMeter.Invalidate(); break; /*case ckmmc::Device::ckPROFILE_BDROM: case ckmmc::Device::ckPROFILE_BDR_SRM: case ckmmc::Device::ckPROFILE_BDR_RRM: case ckmmc::Device::ckPROFILE_BDRE: case ckmmc::Device::ckPROFILE_HDDVDROM: case ckmmc::Device::ckPROFILE_HDDVDR: case ckmmc::Device::ckPROFILE_HDDVDRAM: m_SpaceMeter.SetDiscSize(); m_SpaceMeter.Invalidate(); break;*/ // FIXME: In order to switch to CD size we need to know exactly how much the blank CD can store. /*case ckmmc::Device::ckPROFILE_CDR: case ckmmc::Device::ckPROFILE_CDRW: m_SpaceMeter.SetDiscSize(SPACEMETER_SIZE_703MB); m_SpaceMeter.Invalidate(); break;*/ } } } } } } return 0; } void CMainFrame::DisplayContextMenuOnShellTree(POINT ptPos,bool bWasWithKeyboard) { const HTREEITEM hSelectedItem = m_ShellTreeView.GetSelectedItem(); if (hSelectedItem == NULL) { // Theoretically possible, but I haven't found yet a 'normal' way to get here. ATLASSERT(false); return; } if (bWasWithKeyboard) { // It's possible to scroll the item out of view with the mouse, // and then call up the context menu with the keyboard. m_ShellTreeView.EnsureVisible(hSelectedItem); RECT rcItem; if (FALSE == m_ShellTreeView.GetItemRect(hSelectedItem,&rcItem,TRUE)) throw ckcore::Exception2(_T("GetItemRect: ")); // This "half-way" calculation emulates more or less what Windows Explorer does, // but there is probably a better, "canonical" way to calculate this position. const int iHalfHeight = (rcItem.bottom - rcItem.top) / 2; ptPos.x = rcItem.left + iHalfHeight; ptPos.y = rcItem.top + iHalfHeight; if (FALSE == m_ShellTreeView.ClientToScreen(&ptPos)) { ckcore::throw_from_hresult(GetLastError(),_T("ClientToScreen: ")); } } // We should display here the full shell context menu with CDefFolderMenu_Create2(), // but that's rather difficult. Until I've figured out how to do it, // we'll have to make do with this tiny pop-up menu. if (0 == m_ShellTreeMenu.GetSubMenu(0).TrackPopupMenuEx(0,ptPos.x,ptPos.y,m_hWnd,NULL)) { ckcore::throw_from_hresult(GetLastError(),_T("TrackPopupMenuEx: ")); } } LRESULT CMainFrame::OnSLVBrowseObject(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { HWND hWnd = (HWND)lParam; m_ShellListViewContainer.SetClient(hWnd); bHandled = true; return 0; } LRESULT CMainFrame::OnSLVDoneBrowseObject(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { HTREEITEM hSelectedItem = m_ShellTreeView.GetSelectedItem(); CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)m_ShellTreeView.GetItemData(hSelectedItem); TCHAR szFullName[MAX_PATH]; if (pItemInfo->pParentFolder) { m_PidlHelp.GetDisplayPathName(pItemInfo->pParentFolder,pItemInfo->pidlSelf,szFullName,MAX_PATH - 1); } else { IShellFolder *pDesktopFolder; if (SUCCEEDED(SHGetDesktopFolder(&pDesktopFolder))) { m_PidlHelp.GetDisplayPathName(pDesktopFolder,pItemInfo->pidlFullyQual,szFullName,MAX_PATH - 1); } } // Update the current path. (This is not the same as display name.) if (pItemInfo->pParentFolder) { m_PidlHelp.GetPathName(pItemInfo->pParentFolder,pItemInfo->pidlSelf,szFullName,MAX_PATH - 1); } else { IShellFolder *pDesktopFolder; if (SUCCEEDED(SHGetDesktopFolder(&pDesktopFolder))) { m_PidlHelp.GetPathName(pDesktopFolder,pItemInfo->pidlFullyQual,szFullName,MAX_PATH - 1); } } // Remember the new path if the user has selected that option. if (g_GlobalSettings.m_bRememberShell) lstrcpy(g_DynamicSettings.m_szShellDir,szFullName); bHandled = true; return 0; } bool CMainFrame::OpenSpecialFolder(int iFolder) { LPITEMIDLIST pidl; SHGetSpecialFolderLocation(NULL,iFolder,&pidl); // First the root item (desktop) is expanded. HTREEITEM hRootItem = m_ShellTreeView.GetRootItem(); m_ShellTreeView.Expand(hRootItem); // Then we search desktop item for the special folder. HTREEITEM hItem = m_ShellTreeView.GetChildItem(hRootItem); while (hItem) { CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)m_ShellTreeView.GetItemData(hItem); if (pItemInfo->pParentFolder->CompareIDs(SHCIDS_CANONICALONLY,pItemInfo->pidlSelf,pidl) == 0) { m_bEnableTreeSelection = false; m_ShellTreeView.SelectItem(hItem); m_ShellTreeView.Expand(hItem); m_bEnableTreeSelection = true; return true; } hItem = m_ShellTreeView.GetNextVisibleItem(hItem); } return false; } bool CMainFrame::OpenFolder(TCHAR *szFullPath,HTREEITEM hFrom,bool bExpandMyComp) { // We need to make sure that the "My Computer" item is selected and expaned. if (bExpandMyComp) { if (!OpenSpecialFolder(CSIDL_DRIVES)) return false; } HTREEITEM hItem = m_ShellTreeView.GetChildItem(hFrom); CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)m_ShellTreeView.GetItemData(hItem); TCHAR szCurName[MAX_PATH]; // It's important that we include the trailing backslash on the current path. Otherwise // we might get a false match in the comparison later. IncludeTrailingBackslash(szFullPath); int iFullLength = lstrlen(szFullPath); m_bEnableTreeSelection = false; while (hItem) { pItemInfo = NULL; pItemInfo = (CShellTreeItemInfo *)m_ShellTreeView.GetItemData(hItem); ATLASSERT(pItemInfo != NULL); m_PidlHelp.GetPathName(pItemInfo->pParentFolder,pItemInfo->pidlSelf,szCurName,MAX_PATH - 1); IncludeTrailingBackslash(szCurName); int iCurLength = lstrlen(szCurName); if (!_wcsnicmp(szCurName,szFullPath,iCurLength)) { m_ShellTreeView.SelectItem(hItem); m_ShellTreeView.Expand(hItem); if (iCurLength == iFullLength) break; } hItem = m_ShellTreeView.GetNextVisibleItem(hItem); } m_bEnableTreeSelection = true; return true; } /* CMainFrame::AddFolder --------------------- Add a new folder to the tree. The fullpath should be specified. It returns true upon success, false otherwise. */ bool CMainFrame::AddFolder(TCHAR *szFullPath) { // Get the full pidl of the new folder. LPITEMIDLIST pidl; if (!m_PidlHelp.GetPidl(szFullPath,&pidl)) return false; if (ExtractFilePath(szFullPath)) { // Get the pidl of the parent. LPITEMIDLIST pidlParent; if (!m_PidlHelp.GetPidl(szFullPath,&pidlParent)) return false; // Locate the parent in the tree. HTREEITEM hParentItem = FindItemFromPath(pidlParent); if (!hParentItem) return false; // Why does this event get called twice for some newly created folders. If // SHCNE_MKDIR was received only once we would not have to test this. if (ItemExist(hParentItem,pidl)) return false; // Check if the file doesn't have any children. If that is the case, we // should not add the new items, just update the item count. The item // will be added automaticly when expanding the node. TVITEMEX tvParentItem; tvParentItem.hItem = hParentItem; tvParentItem.mask = TVIF_CHILDREN | TVIF_STATE; if (m_ShellTreeView.GetItem(&tvParentItem)) { if (tvParentItem.cChildren == 0 || !(tvParentItem.state & TVIS_EXPANDEDONCE)) { tvParentItem.cChildren = 1; m_ShellTreeView.SetItem(&tvParentItem); return true; } } // The parent already has children so we need to add the new folder manually. CShellTreeItemInfo *pParentInfo = (CShellTreeItemInfo *)m_ShellTreeView.GetItemData(hParentItem); LPITEMIDLIST parentpidl,childpidl; m_PidlHelp.Split(pidl,&parentpidl,&childpidl); IShellFolder *pParentFolder; // If the parent has no parent, the desktop should be used as parent. if (pParentInfo->pParentFolder == 0) { if (FAILED(SHGetDesktopFolder(&pParentFolder))) return false; } else if (FAILED(pParentInfo->pParentFolder->BindToObject(pParentInfo->pidlSelf, NULL,IID_IShellFolder,(void **)&pParentFolder))) { return false; } TV_ITEM tvItem = { 0 }; TV_INSERTSTRUCT tvInsert = { 0 }; DWORD dwAttribs; CShellTreeItemInfo *pItemInfo = new CShellTreeItemInfo; pItemInfo->pidlSelf = childpidl; // We can't use ppidls[0], we need to allocate our own one. pItemInfo->pidlFullyQual = m_PidlHelp.ConcatenatePidl(parentpidl,childpidl);; pParentFolder->AddRef(); pItemInfo->pParentFolder = pParentFolder; ZeroMemory(&tvItem,sizeof(tvItem)); tvItem.mask = TVIF_PARAM | TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_CHILDREN; tvItem.pszText = LPSTR_TEXTCALLBACK; tvItem.iImage = tvItem.iSelectedImage = I_IMAGECALLBACK; tvItem.lParam = (LPARAM)pItemInfo; dwAttribs = SFGAO_HASSUBFOLDER | SFGAO_FOLDER | /*SFGAO_DISPLAYATTRMASK | */SFGAO_CANRENAME; pParentFolder->GetAttributesOf(1,(LPCITEMIDLIST *)&childpidl,&dwAttribs); tvItem.cChildren = (dwAttribs & SFGAO_HASSUBFOLDER); if (dwAttribs & SFGAO_SHARE) { tvItem.mask |= TVIF_STATE; tvItem.stateMask |= TVIS_OVERLAYMASK; tvItem.state |= INDEXTOOVERLAYMASK(1); } tvInsert.item = tvItem; tvInsert.hInsertAfter = TVI_LAST; //tvInsert.hInsertAfter = TVI_SORT; tvInsert.hParent = hParentItem; // Insert the tree item. m_ShellTreeView.InsertItem(&tvInsert); pParentFolder->Release(); } return true; } /* CMainFrame::RemoveFolder -------.---------------- Removes a node from the tree. The item data is freed. It returns true if no errors occured and false otherwise. */ bool CMainFrame::RemoveFolder(LPITEMIDLIST pidlFullyQual) { // Locate the item in the tree. HTREEITEM hItem = FindItemFromPath(pidlFullyQual); if (!hItem) return false; if (SUCCEEDED(m_ShellTreeView.DeleteItem(hItem))) return true; return false; } /* CMainFrame::RenameFolder ------------------------ Renames the tree item and updates the pidl accordingly. It returns true if no errors occured and false otherwise. */ bool CMainFrame::RenameFolder(LPITEMIDLIST pidlOldFullyQual,LPITEMIDLIST pidlNewFullyQual) { // Locate the item in the tree. HTREEITEM hItem = FindItemFromPath(pidlOldFullyQual); if (!hItem) return false; CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)m_ShellTreeView.GetItemData(hItem); if (!pItemInfo) return false; // Extract the full path name from the new pidl. TCHAR szFullPath[MAX_PATH]; m_PidlHelp.GetPathName(pidlNewFullyQual,szFullPath); // Compare the two paths where the new folder and old folder are located. // If they differ the folder has been moved, otherwise we can just rename the // existing one. TCHAR szOldFullPath[MAX_PATH]; m_PidlHelp.GetPathName(pidlOldFullyQual,szOldFullPath); TCHAR szTemp[MAX_PATH]; lstrcpy(szTemp,szFullPath); ExtractFilePath(szOldFullPath); ExtractFilePath(szTemp); // If the paths match move the folder. if (lstrcmp(szTemp,szOldFullPath)) return MoveFolder(pidlOldFullyQual,szFullPath); // Generate a new pidl from the path name above. (Why doesn't the first work?) LPITEMIDLIST pidlNew; if (!m_PidlHelp.GetPidl(szFullPath,&pidlNew)) return false; // Split the pidl into parent and child parts. LPITEMIDLIST pidlParent,pidlChild; m_PidlHelp.Split(pidlNew,&pidlParent,&pidlChild); pItemInfo->pidlSelf = pidlChild; // We can't use pidlOldFullyQual, we need to allocate our own one. pItemInfo->pidlFullyQual = m_PidlHelp.ConcatenatePidl(pidlParent,pidlChild); // Manually update the tree item text. SHFILEINFO shFileInfo; if (SHGetFileInfo((LPCTSTR)pItemInfo->pidlFullyQual,0,&shFileInfo, sizeof(shFileInfo),SHGFI_PIDL | SHGFI_DISPLAYNAME)) { m_ShellTreeView.SetItemText(hItem,shFileInfo.szDisplayName); } // Sort all children to the active parent (not recursive). // Update: I don't want to sort the tree. This will prevent all system folder // to stay at top in the tree. //m_ShellTreeView.SortChildren(m_ShellTreeView.GetParentItem(hItem),FALSE); return true; } bool CMainFrame::MoveFolder(LPITEMIDLIST pidlFullyQual,TCHAR *szNewName) { if (RemoveFolder(pidlFullyQual)) return AddFolder(szNewName); return false; } bool CMainFrame::ItemExist(HTREEITEM hParentItem,LPITEMIDLIST pidl) { HTREEITEM hItem = m_ShellTreeView.GetChildItem(hParentItem); while (hItem) { CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)m_ShellTreeView.GetItemData(hItem); if (pItemInfo) { TCHAR szPath1[MAX_PATH],szPath2[MAX_PATH]; m_PidlHelp.GetPathName(pidl,szPath1); m_PidlHelp.GetPathName(pItemInfo->pidlFullyQual,szPath2); if (!lstrcmp(szPath1,szPath2)) return true; } hItem = m_ShellTreeView.GetNextVisibleItem(hItem); } return false; } HTREEITEM CMainFrame::FindItemFromPath(LPITEMIDLIST pidl) { HTREEITEM hItem = m_ShellTreeView.GetRootItem(); while (hItem) { CShellTreeItemInfo *pItemInfo = NULL; pItemInfo = (CShellTreeItemInfo *)m_ShellTreeView.GetItemData(hItem); TCHAR szPath1[MAX_PATH],szPath2[MAX_PATH]; m_PidlHelp.GetPathName(pidl,szPath1); m_PidlHelp.GetPathName(pItemInfo->pidlFullyQual,szPath2); if (!lstrcmp(szPath1,szPath2)) return hItem; hItem = m_ShellTreeView.GetNextVisibleItem(hItem); } return 0; } LRESULT CMainFrame::OnSLVChangeFolder(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { //const LPCITEMIDLIST pidl = (LPCITEMIDLIST)wParam; const TCHAR *szNewPathName = (TCHAR *)lParam; TCHAR szFullPath[MAX_PATH]; lstrcpy(szFullPath,szNewPathName); // We must expand the current node. m_ShellTreeView.Expand(m_ShellTreeView.GetSelectedItem()); // Open the path in the tree view, there is no need to expand the My Computer // node since the path is relative. OpenFolder(szFullPath,m_ShellTreeView.GetSelectedItem(),false); bHandled = true; return 0; } LRESULT CMainFrame::OnSLVChangeFolderLink(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { //const LPCITEMIDLIST pidl = (LPCITEMIDLIST)wParam; const TCHAR *szNewPathName = (TCHAR *)lParam; TCHAR szFullPath[MAX_PATH]; lstrcpy(szFullPath,szNewPathName); // Go to the link path, the My Computer node needs to be expanded. OpenFolder(szFullPath,m_ShellTreeView.GetSelectedItem(),true); bHandled = true; return 0; } bool CMainFrame::EnumTreeObjects(HTREEITEM hParentItem,IShellFolder* pParentFolder,LPITEMIDLIST pidlParent) { IEnumIDList *pEnum; if (SUCCEEDED(pParentFolder->EnumObjects(NULL,SHCONTF_FOLDERS | SHCONTF_INCLUDEHIDDEN,&pEnum))) { ITEMIDLIST *pidl; DWORD dwFetched = 1; DWORD dwAttribs; TV_ITEM tvItem = {0}; TV_INSERTSTRUCT tvInsert = {0}; while (SUCCEEDED(pEnum->Next(1,&pidl,&dwFetched)) && dwFetched) { CShellTreeItemInfo *pItemInfo = new CShellTreeItemInfo(); pItemInfo->pidlSelf = pidl; pItemInfo->pidlFullyQual = m_PidlHelp.ConcatenatePidl(pidlParent,pidl); pParentFolder->AddRef(); pItemInfo->pParentFolder = pParentFolder; ZeroMemory(&tvItem,sizeof(tvItem)); tvItem.mask = TVIF_PARAM | TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_CHILDREN; tvItem.pszText = LPSTR_TEXTCALLBACK; tvItem.iImage = tvItem.iSelectedImage = I_IMAGECALLBACK; tvItem.lParam = (LPARAM)pItemInfo; // UPDATE: SFGAO_DISPLAYATTRMASK should never be used according to MSDN documentation. /*SHDESCRIPTIONID sdiDesc; bool bIsFloppy = false; if (SUCCEEDED(SHGetDataFromIDList(pParentFolder,pidl,SHGDFIL_DESCRIPTIONID,&sdiDesc,sizeof(sdiDesc)))) { if (sdiDesc.dwDescriptionId == SHDID_COMPUTER_DRIVE35 || sdiDesc.dwDescriptionId == SHDID_COMPUTER_DRIVE525) bIsFloppy = true; } if (bIsFloppy) { dwAttribs = SFGAO_HASSUBFOLDER | SFGAO_FOLDER | SFGAO_CANRENAME; pParentFolder->GetAttributesOf(1,(LPCITEMIDLIST *)&pidl,&dwAttribs); } else { dwAttribs = SFGAO_HASSUBFOLDER | SFGAO_FOLDER | SFGAO_DISPLAYATTRMASK | SFGAO_CANRENAME; pParentFolder->GetAttributesOf(1,(LPCITEMIDLIST *)&pidl,&dwAttribs); }*/ dwAttribs = SFGAO_HASSUBFOLDER | SFGAO_FOLDER | SFGAO_CANRENAME; pParentFolder->GetAttributesOf(1,(LPCITEMIDLIST *)&pidl,&dwAttribs); tvItem.cChildren = (dwAttribs & SFGAO_HASSUBFOLDER); if (dwAttribs & SFGAO_SHARE) { tvItem.mask |= TVIF_STATE; tvItem.stateMask |= TVIS_OVERLAYMASK; tvItem.state |= INDEXTOOVERLAYMASK(1); } tvInsert.item = tvItem; tvInsert.hInsertAfter = TVI_LAST; tvInsert.hParent = hParentItem; // Insert the tree item. m_ShellTreeView.InsertItem(&tvInsert); dwFetched = 0; } pEnum->Release(); return true; } return false; } LRESULT CMainFrame::OnSTVGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { LPNMTVDISPINFO lpDispInfo = (LPNMTVDISPINFO)pNMH; CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)lpDispInfo->item.lParam; SHFILEINFO shFileInfo; if (lpDispInfo->item.mask & TVIF_TEXT) { if (SHGetFileInfo((LPCTSTR)pItemInfo->pidlFullyQual,0,&shFileInfo, sizeof(shFileInfo),SHGFI_PIDL | SHGFI_DISPLAYNAME)) { lstrcpy(lpDispInfo->item.pszText,shFileInfo.szDisplayName); } } if (lpDispInfo->item.mask & TVIF_IMAGE) { if (SHGetFileInfo((LPCTSTR)pItemInfo->pidlFullyQual,0,&shFileInfo, sizeof(shFileInfo),SHGFI_PIDL | SHGFI_SYSICONINDEX | SHGFI_SMALLICON | SHGFI_LINKOVERLAY)) { lpDispInfo->item.iImage = shFileInfo.iIcon; } } if (lpDispInfo->item.mask & TVIF_SELECTEDIMAGE) { if (SHGetFileInfo((LPCTSTR)pItemInfo->pidlFullyQual,0,&shFileInfo, sizeof(shFileInfo),SHGFI_PIDL | SHGFI_SYSICONINDEX | SHGFI_SMALLICON | SHGFI_OPENICON)) { lpDispInfo->item.iSelectedImage = shFileInfo.iIcon; } } bHandled = false; return 0; } LRESULT CMainFrame::OnSTVItemExpanding(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { LPNMTREEVIEW pNMTV = (LPNMTREEVIEW)pNMH; bHandled = false; if (pNMTV->action == TVE_COLLAPSE) { m_ShellTreeView.Expand(pNMTV->itemNew.hItem, TVE_COLLAPSE | TVE_COLLAPSERESET); } else if (pNMTV->action == TVE_EXPAND) { HCURSOR hCursor; TVITEM tvItem = {0}; tvItem.mask = TVIF_PARAM; tvItem.hItem = pNMTV->itemNew.hItem; if (!m_ShellTreeView.GetItem(&tvItem)) return 0; CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)tvItem.lParam; hCursor = SetCursor(LoadCursor(NULL,IDC_WAIT)); IShellFolder *pParentFolder = NULL; if (pItemInfo->pParentFolder == 0) { if (FAILED(SHGetDesktopFolder(&pParentFolder))) return 0; } else if (FAILED(pItemInfo->pParentFolder->BindToObject(pItemInfo->pidlSelf, NULL,IID_IShellFolder,(void **)&pParentFolder))) { return 0; } m_ShellTreeView.SetRedraw(FALSE); EnumTreeObjects(pNMTV->itemNew.hItem,pParentFolder, pItemInfo->pidlFullyQual); m_ShellTreeView.SetRedraw(TRUE); pParentFolder->Release(); SetCursor(hCursor); } return 0; } LRESULT CMainFrame::OnSTVDeleteItem(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { LPNMTREEVIEW pNMTV = (LPNMTREEVIEW)pNMH; IMalloc *pMalloc; CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)pNMTV->itemOld.lParam; if (SUCCEEDED(SHGetMalloc(&pMalloc))) { if (pItemInfo->dwFlags == 0) { pMalloc->Free(pItemInfo->pidlSelf); pMalloc->Release(); if (pItemInfo->pParentFolder) { pItemInfo->pParentFolder->Release(); pMalloc->Free(pItemInfo->pidlFullyQual); } } } delete pItemInfo; bHandled = false; return 0; } LRESULT CMainFrame::OnSTVSelChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { bHandled = false; if (!m_bEnableTreeSelection) return 0; LPNMTREEVIEW pNMTV = (LPNMTREEVIEW)pNMH; CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)pNMTV->itemNew.lParam; // This check should not be needed. However if some syncronization error between the // shell list view and shell tree view occur this pItemInfo might be NULL. if (!pItemInfo) return 0; if (pItemInfo->dwFlags == 0) { if (pItemInfo->pParentFolder == 0) m_pShellListView->BrowseObject(pItemInfo->pidlSelf,SBSP_SAMEBROWSER | SBSP_ABSOLUTE); else m_pShellListView->BrowseObject(pItemInfo->pidlFullyQual,SBSP_SAMEBROWSER | SBSP_ABSOLUTE); } return 0; } LRESULT CMainFrame::OnSTVBeginDrag(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { bHandled = false; if (!m_bEnableTreeSelection) return 0; LPNMTREEVIEW pNMTV = (LPNMTREEVIEW)pNMH; CShellTreeItemInfo *pItemInfo = (CShellTreeItemInfo *)pNMTV->itemNew.lParam; // This check should not be needed. However if some syncronization error between the // shell list view and shell tree view occur this pItemInfo might be NULL. if (!pItemInfo) return 0; TCHAR szFileName[MAX_PATH]; if (pItemInfo->pParentFolder) { m_PidlHelp.GetPathName(pItemInfo->pParentFolder,pItemInfo->pidlSelf,szFileName,MAX_PATH - 1); } else { IShellFolder *pDesktopFolder; if (SUCCEEDED(SHGetDesktopFolder(&pDesktopFolder))) { m_PidlHelp.GetPathName(pDesktopFolder,pItemInfo->pidlFullyQual,szFileName,MAX_PATH - 1); } } // We don't allow dragging special system items with virtual file names that begins with "::{". if (szFileName[0] == ':') return 0; CProjectDropSource *pDropSource = new CProjectDropSource(); CFilesDataObject *pDataObject = new CFilesDataObject(); // Add all file names to the data object. pDataObject->AddFile(szFileName); DWORD dwEffect = 0; ::DoDragDrop(pDataObject,pDropSource,DROPEFFECT_COPY,&dwEffect); pDropSource->Release(); pDataObject->Release(); return 0; } LRESULT CMainFrame::OnSTVRClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { try { // Code inspired by this FAQ question: // Why don't I get a WM_CONTEXTMENU message when I right click in a Tree Control? // http://vcfaq.mvps.org/mfc/6.htm ATLASSERT(pNMH->hwndFrom == m_ShellTreeView.m_hWnd); // Whether we succeed or fail, we are the only place to process this notification. bHandled = TRUE; // Get the mouse cursor position. const DWORD dwPos = GetMessagePos(); POINT ptPos; ptPos.x = GET_X_LPARAM(dwPos); ptPos.y = GET_Y_LPARAM(dwPos); // Convert to screen co-ords for hit testing. if (FALSE == m_ShellTreeView.ScreenToClient(&ptPos)) { ckcore::throw_from_hresult(GetLastError(),_T("ScreenToClient: ")); } UINT uHitTestFlags; const HTREEITEM hHitItem = m_ShellTreeView.HitTest(ptPos,&uHitTestFlags); // Did the click occur on an item? if ((hHitItem != NULL) && (uHitTestFlags & TVHT_ONITEM)) { // Select the item only if we are going to open the pop-up menu // for it. This is the same behaviour I've observed with Windows Explorer. ATLVERIFY(TRUE == m_ShellTreeView.SelectItem(hHitItem)); // Simulate WM_CONTEXTMENU. BOOL bOnContextMenuHandled = FALSE; OnContextMenu(WM_CONTEXTMENU,WPARAM(pNMH->hwndFrom),dwPos,bOnContextMenuHandled); ATLASSERT(bOnContextMenuHandled == TRUE); } } catch (const std::exception &e) { ATLVERIFY(IDOK == MessageBox(ckcore::get_except_msg(e).c_str(), lngGetString(GENERAL_ERROR), MB_OK | MB_ICONERROR)); } return 0; } LRESULT CMainFrame::OnPTVGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { LPNMTVDISPINFO lpDispInfo = (LPNMTVDISPINFO)pNMH; CProjectNode *pNode = (CProjectNode *)lpDispInfo->item.lParam; if (lpDispInfo->item.mask & TVIF_TEXT) lstrcpy(lpDispInfo->item.pszText,pNode->pItemData->GetFileName()); bHandled = false; return 0; } LRESULT CMainFrame::OnPTVSelChanging(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { // If a mixed-mode project is active we want to prevent the root node from // beeing selected. if (g_ProjectManager.GetProjectType() == PROJECTTYPE_MIXED) { LPNMTREEVIEW lpDispInfo = (LPNMTREEVIEW)pNMH; CProjectNode *pNode = (CProjectNode *)lpDispInfo->itemNew.lParam; if (pNode == g_TreeManager.GetRootNode()) { bHandled = true; return TRUE; } } bHandled = false; return 0; } LRESULT CMainFrame::OnPTVSelChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { LPNMTREEVIEW pNMTV = (LPNMTREEVIEW)pNMH; bool bChangePath = true; int iImage,iSelImage; iImage = iSelImage = -1; m_ProjectTreeView.GetItemImage(pNMTV->itemNew.hItem,iImage,iSelImage); switch (iImage) { case PROJECTTREE_IMAGEINDEX_MIXED: bChangePath = false; break; case PROJECTTREE_IMAGEINDEX_AUDIO: g_ProjectManager.AudioSelected(); break; default: g_ProjectManager.DataSelected(); break; }; // Select the new path. CProjectNode *pNode = (CProjectNode *)pNMTV->itemNew.lParam; if (bChangePath) { TCHAR szNewPath[MAX_PATH]; lstrcpy(szNewPath,pNode->pItemData->GetFilePath()); lstrcat(szNewPath,pNode->pItemData->GetFileName()); lstrcat(szNewPath,_T("\\")); g_TreeManager.SelectPath(szNewPath); } // Update the project manager. g_ProjectManager.TreeSetActionNode(pNode); // Update the menu items if focused. if (::GetFocus() == m_ProjectTreeView) g_ProjectManager.NotifyTreeSelChanged(pNode); bHandled = false; return 0; } LRESULT CMainFrame::OnPTVBeginLabelEdit(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { LPNMTVDISPINFO lpDispInfo = (LPNMTVDISPINFO)pNMH; CProjectNode *pNode = (CProjectNode *)lpDispInfo->item.lParam; // We want to prevent the root and virtual audio root node from beeing // renamed if we are dealing with a mixed project. if (g_ProjectManager.GetProjectType() == PROJECTTYPE_MIXED) { if (pNode == g_ProjectManager.GetMixAudioRootNode()) { bHandled = true; return TRUE; } } // We can't rename locked items. if (pNode->pItemData->ucFlags & PROJECTITEM_FLAG_ISLOCKED) { bHandled = true; return TRUE; } // Disable all accelerators. m_bEnableAccel = false; bHandled = false; return 0; } LRESULT CMainFrame::OnPTVEndLabelEdit(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { bHandled = true; // Enable the accelerators. m_bEnableAccel = true; // Check for an empty name. LPNMTVDISPINFO lpDispInfo = (LPNMTVDISPINFO)pNMH; if (lpDispInfo->item.pszText == NULL || lpDispInfo->item.pszText[0] == '\0') return TRUE; // Make sure that file name does not contain illegal characters. if (FirstDelimiter(lpDispInfo->item.pszText,'\\') != -1 || FirstDelimiter(lpDispInfo->item.pszText,'/') != -1) { return TRUE; } CProjectNode *pNode = (CProjectNode *)lpDispInfo->item.lParam; if (pNode != g_TreeManager.GetRootNode()) { // Update the file name. pNode->pItemData->SetFileName(lpDispInfo->item.pszText); TCHAR szFullName[MAX_PATH]; lstrcpy(szFullName,pNode->pItemData->GetFilePath()); lstrcat(szFullName,pNode->pItemData->GetFileName()); lstrcat(szFullName,_T("\\")); g_TreeManager.RebuildPaths(szFullName); m_ProjectListView.ForceRedraw(); if (g_ProjectManager.GetProjectType() == PROJECTTYPE_MIXED && pNode == g_ProjectManager.GetMixDataRootNode()) { lstrcpy(g_ProjectSettings.m_szLabel,lpDispInfo->item.pszText); } if (pNode == g_TreeManager.GetCurrentNode()) g_TreeManager.SetCurrentPath(szFullName); } else { // Update label. if (g_ProjectManager.GetProjectType() == PROJECTTYPE_DATA) lstrcpy(g_ProjectSettings.m_szLabel,lpDispInfo->item.pszText); } g_ProjectManager.SetModified(true); return TRUE; } LRESULT CMainFrame::OnPTVBeginDrag(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { m_ProjectTreeView.BeginDrag((LPNMTREEVIEW)pNMH); bHandled = false; return 0; } LRESULT CMainFrame::OnPTVRClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { POINT CursorPos,ClientPos; GetCursorPos(&CursorPos); ClientPos = CursorPos; ::ScreenToClient(pNMH->hwndFrom,&ClientPos); TVHITTESTINFO tvHitTestInfo = { 0 }; tvHitTestInfo.pt = ClientPos; m_ProjectTreeView.HitTest(&tvHitTestInfo); if ((tvHitTestInfo.flags & TVHT_ONITEMLABEL) != 0) { //m_ProjectTreeView.EditLabel(tvHitTestInfo.hItem); TVITEM tvItem = { 0 }; tvItem.mask = TVIF_PARAM; tvItem.hItem = tvHitTestInfo.hItem; if (m_ProjectTreeView.GetItem(&tvItem) != FALSE) { g_ProjectManager.TreeSetActionNode((CProjectNode *)tvItem.lParam); g_ProjectManager.NotifyTreeSelChanged((CProjectNode *)tvItem.lParam); // TrackPopupMenuEx is asynchronous, it may return before the WM_COMMAND // message is sent. This walkaround forces the WM_COMMAND message to be // processed before this function returns. int iID = TrackPopupMenuEx(GetSubMenu(m_hProjListSelMenu,0),TPM_NONOTIFY | TPM_RETURNCMD,CursorPos.x,CursorPos.y,m_hWnd,NULL); ::SendMessage(m_hWnd,WM_COMMAND,(WPARAM)iID,NULL); } } g_ProjectManager.NotifyTreeSelChanged((CProjectNode *)m_ProjectTreeView.GetSelectedItem().GetData()); bHandled = false; return 0; } LRESULT CMainFrame::OnPLVGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { NMLVDISPINFO *pDispInfo = (NMLVDISPINFO *)pNMH; CItemData *pItemData = (CItemData *)pDispInfo->item.lParam; LVCOLUMN lvColumn = { 0 }; lvColumn.mask = LVCF_SUBITEM; m_ProjectListView.GetColumn(pDispInfo->item.iSubItem,&lvColumn); if (pDispInfo->item.mask & LVIF_IMAGE) { SHFILEINFO shFileInfo; if (pItemData->ucFlags & PROJECTITEM_FLAG_ISFOLDER) { // HACK: Force a folder icon to be used. if (SHGetFileInfo(_T(""),FILE_ATTRIBUTE_DIRECTORY,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_SYSICONINDEX)) { pDispInfo->item.iImage = shFileInfo.iIcon; } } else { if (SHGetFileInfo(pItemData->GetFileName(),FILE_ATTRIBUTE_NORMAL,&shFileInfo, sizeof(shFileInfo), SHGFI_USEFILEATTRIBUTES | SHGFI_SYSICONINDEX)) { pDispInfo->item.iImage = shFileInfo.iIcon; } } } if (pDispInfo->item.mask & LVIF_TEXT) { if (g_ProjectManager.GetViewType() == PROJECTVIEWTYPE_DATA) { switch (lvColumn.iSubItem) { case COLUMN_SUBINDEX_NAME: lstrcpy(pDispInfo->item.pszText,pItemData->GetFileName()); break; case COLUMN_SUBINDEX_TYPE: lstrcpy(pDispInfo->item.pszText,pItemData->szFileType); break; case COLUMN_SUBINDEX_MODIFIED: wsprintf(pDispInfo->item.pszText,_T("%04u-%02u-%02u %02u:%02u:%02u"), (pItemData->usFileDate >> 9) + 1980, (pItemData->usFileDate >> 5) & 0x0F, (pItemData->usFileDate & 0x1F), (pItemData->usFileTime >> 11), (pItemData->usFileTime >> 5) & 0x3F, (pItemData->usFileTime & 0x1F) * 2); break; case COLUMN_SUBINDEX_SIZE: if (pItemData->ucFlags & PROJECTITEM_FLAG_ISFOLDER) pDispInfo->item.pszText[0] = '\0'; else lsprintf(pDispInfo->item.pszText,_T("%I64d"),pItemData->uiSize); break; case COLUMN_SUBINDEX_PATH: lstrcpy(pDispInfo->item.pszText,pItemData->GetFilePath()); break; } } else { switch (lvColumn.iSubItem) { case COLUMN_SUBINDEX_TRACK: if ((unsigned int)pDispInfo->item.pszText != 0xFFFFFFFF) lsprintf(pDispInfo->item.pszText,_T("%d"),pDispInfo->item.iItem + 1); break; case COLUMN_SUBINDEX_TITLE: // If no title is specified the file name is displayed. if (pItemData->GetAudioData()->szTrackTitle[0] == '\0') lstrcpy(pDispInfo->item.pszText,pItemData->GetFileName()); else lstrcpy(pDispInfo->item.pszText,pItemData->GetAudioData()->szTrackTitle); break; case COLUMN_SUBINDEX_LENGTH: lsprintf(pDispInfo->item.pszText,_T("%.2d:%.2d:%.2d"), (unsigned int)(pItemData->GetAudioData()->uiTrackLength/(1000 * 3600)), (unsigned int)((pItemData->GetAudioData()->uiTrackLength/(1000 * 60)) % 60), (unsigned int)((pItemData->GetAudioData()->uiTrackLength/1000) % 60)); break; case COLUMN_SUBINDEX_LOCATION: lstrcpy(pDispInfo->item.pszText,pItemData->szFullPath); break; } } } bHandled = false; return 0; } LRESULT CMainFrame::OnPLVBeginLabelEdit(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { NMLVDISPINFO *pDispInfo = (NMLVDISPINFO *)pNMH; CItemData *pItemData = (CItemData *)pDispInfo->item.lParam; // We can't rename locked items. if (pItemData->ucFlags & PROJECTITEM_FLAG_ISLOCKED) { bHandled = true; return TRUE; } // Disable all accelerators. m_bEnableAccel = false; bHandled = false; return 0; } LRESULT CMainFrame::OnPLVEndLabelEdit(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { bHandled = true; // Enable the accelerators. m_bEnableAccel = true; // Check for an empty name. NMLVDISPINFO *pDispInfo = (NMLVDISPINFO *)pNMH; if (pDispInfo->item.pszText == NULL || pDispInfo->item.pszText[0] == '\0') return TRUE; // Make sure that file name does not contain illegal characters. if (FirstDelimiter(pDispInfo->item.pszText,'\\') != -1 || FirstDelimiter(pDispInfo->item.pszText,'/') != -1) { return TRUE; } // Check for an existing file or folder with the same name. if (g_TreeManager.GetChildItem(g_TreeManager.GetCurrentNode(),pDispInfo->item.pszText) != NULL) { TCHAR szMessage[MAX_PATH]; lsnprintf_s(szMessage,sizeof(szMessage),lngGetString(ERROR_EXISTINGFILENAME), pDispInfo->item.pszText); MessageBox(szMessage,lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return TRUE; } // FIXME: A name check should be performed before accepting the name change. // The file name might contain illegal characters. // Update the file name. CItemData *pItemData = (CItemData *)pDispInfo->item.lParam; pItemData->SetFileName(pDispInfo->item.pszText); // Update the file type (if it's not a folder). if (!(pItemData->ucFlags & PROJECTITEM_FLAG_ISFOLDER)) { SHFILEINFO shFileInfo; if (SHGetFileInfo(pItemData->GetFileName(),FILE_ATTRIBUTE_NORMAL,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_TYPENAME)) { lstrcpy(pItemData->szFileType,shFileInfo.szTypeName); } else { lstrcpy(pItemData->szFileType,_T("")); } } else { TCHAR szFullName[MAX_PATH]; lstrcpy(szFullName,pItemData->GetFilePath()); lstrcat(szFullName,pItemData->GetFileName()); lstrcat(szFullName,_T("\\")); g_TreeManager.RebuildPaths(szFullName); } // Force the tree view to update. RECT rcTree; m_ProjectTreeView.GetClientRect(&rcTree); m_ProjectTreeView.InvalidateRect(&rcTree); g_ProjectManager.SetModified(true); return TRUE; } LRESULT CMainFrame::OnPLVDblClk(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { // First we make sure that an item is selected. int iSelItem = -1; iSelItem = m_ProjectListView.GetNextItem(iSelItem,LVNI_SELECTED); if (iSelItem == -1) return 0; CItemData *pItemData = (CItemData *)m_ProjectListView.GetItemData(iSelItem); if (pItemData != NULL) { // If we double-clicked on a folder we should browse its contents. if (pItemData->ucFlags & PROJECTITEM_FLAG_ISFOLDER) { // Select the folder in the tree view. HTREEITEM hTreeItem = m_ProjectTreeView.GetSelectedItem(); m_ProjectTreeView.Expand(hTreeItem); hTreeItem = m_ProjectTreeView.GetChildItem(hTreeItem); while (hTreeItem) { CProjectNode *pTreeNode = (CProjectNode *)m_ProjectTreeView.GetItemData(hTreeItem); if (pTreeNode) { //if (!lstrcmp(pTreeNode->pItemData->GetFileName(),pItemData->GetFileName())) if (pTreeNode->pItemData == pItemData) { m_ProjectTreeView.SelectItem(hTreeItem); break; } } hTreeItem = m_ProjectTreeView.GetNextVisibleItem(hTreeItem); } } } bHandled = false; return 0; } LRESULT CMainFrame::OnPLVRClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { POINT CursorPos; GetCursorPos(&CursorPos); // Display different popup menus depending on if any item(s) is selected or not. if (m_ProjectListView.GetSelectedCount() > 0) TrackPopupMenuEx(GetSubMenu(m_hProjListSelMenu,0),0,CursorPos.x,CursorPos.y,m_hWnd,NULL); else TrackPopupMenuEx(GetSubMenu(m_hProjListNoSelMenu,0),0,CursorPos.x,CursorPos.y,m_hWnd,NULL); bHandled = false; return 0; } LRESULT CMainFrame::OnPLVItemChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { if (::GetFocus() == m_ProjectListView) g_ProjectManager.NotifyListSelChanged(m_ProjectListView.GetSelectedCount()); bHandled = false; return 0; } LRESULT CMainFrame::OnPLVDeleteItem(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { g_ProjectManager.NotifyListSelChanged(0); bHandled = false; return 0; } LRESULT CMainFrame::OnPLVBeginDrag(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { m_ProjectListView.BeginDrag((LPNMLISTVIEW)pNMH); bHandled = false; return 0; } LRESULT CMainFrame::OnPLVColumnClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { LPNMLISTVIEW lpNMListView = (LPNMLISTVIEW)pNMH; // The 'Track' column in audio projects should not be sortable. if (g_ProjectManager.GetViewType() == PROJECTVIEWTYPE_AUDIO && lpNMListView->iSubItem == 0) return 0; m_ProjectListViewHeader.ColumnClick(lpNMListView->iSubItem); bHandled = false; return 0; } LRESULT CMainFrame::OnToolTipGetInfo(int idCtrl,LPNMHDR pNMH,BOOL &bHandled) { bHandled = true; // The string ID is the same as the button ID. LPTOOLTIPTEXT pTipText = (LPTOOLTIPTEXT)pNMH; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a hint translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("hint"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr((unsigned long)pTipText->hdr.idFrom,szStrValue)) { pTipText->lpszText = szStrValue; return 0; } } } pTipText->lpszText = MAKEINTRESOURCE(pTipText->hdr.idFrom); return 0; } LRESULT CMainFrame::OnMenuSelect(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (g_LanguageSettings.m_pLngProcessor == NULL) { bHandled = false; return TRUE; } // Make sure that there is a hint translation section. if (!g_LanguageSettings.m_pLngProcessor->EnterSection(_T("hint"))) { bHandled = false; return TRUE; } int iIndex = LOWORD(wParam); int iFlags = HIWORD(wParam); if (!(iFlags & MF_POPUP)) { TCHAR szTemp[25]; lsprintf(szTemp,_T("%d (%d)"),iIndex,(int)((iFlags & MF_POPUP) > 0)); TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(iIndex,szStrValue)) ::SendMessage(m_hWndStatusBar,SB_SETTEXT,0,(LPARAM)szStrValue); } else { ::SendMessage(m_hWndStatusBar,SB_SETTEXT,0,(LPARAM)_T("")); } bHandled = true; return 0; } LRESULT CMainFrame::OnNewProjectDataCD(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (!SaveProjectPrompt()) return 0; // Disable the welcome screen if active. ShowWelcomePane(false); SetTitleNormal(); m_szProjectFile[0] = '\0'; g_ProjectManager.NewDataProject(SPACEMETER_SIZE_703MB); return 0; } LRESULT CMainFrame::OnNewProjectDataCDMS(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (!SaveProjectPrompt()) return 0; // Disable the welcome screen if active. ShowWelcomePane(false); SetTitleNormal(); m_szProjectFile[0] = '\0'; g_ProjectManager.NewDataProject(SPACEMETER_SIZE_703MB); g_ProjectSettings.m_iFileSystem = FILESYSTEM_ISO; g_ProjectSettings.m_iIsoFormat = 1; // Mode 2 (multi-session). return 0; } LRESULT CMainFrame::OnNewProjectDataDVD(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (!SaveProjectPrompt()) return 0; // Disable the welcome screen if active. ShowWelcomePane(false); SetTitleNormal(); m_szProjectFile[0] = '\0'; g_ProjectManager.NewDataProject(SPACEMETER_SIZE_DVD); return 0; } LRESULT CMainFrame::OnNewProjectAudio(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (!SaveProjectPrompt()) return 0; // Disable the welcome screen if active. ShowWelcomePane(false); SetTitleNormal(); m_szProjectFile[0] = '\0'; g_ProjectManager.NewAudioProject(SPACEMETER_SIZE_80MIN); return 0; } LRESULT CMainFrame::OnNewProjectMixed(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (!SaveProjectPrompt()) return 0; // Disable the welcome screen if active. ShowWelcomePane(false); SetTitleNormal(); m_szProjectFile[0] = '\0'; g_ProjectManager.NewMixedProject(SPACEMETER_SIZE_703MB); return 0; } LRESULT CMainFrame::OnNewProjectDVDVideo(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (!SaveProjectPrompt()) return 0; // Disable the welcome screen if active. ShowWelcomePane(false); SetTitleNormal(); m_szProjectFile[0] = '\0'; g_ProjectManager.NewDataProject(SPACEMETER_SIZE_DVD); g_ProjectSettings.m_iFileSystem = FILESYSTEM_DVDVIDEO; return 0; } LRESULT CMainFrame::OnFileOpen(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (!SaveProjectPrompt()) return 0; WTL::CFileDialog FileDialog(true,0,0,OFN_FILEMUSTEXIST | OFN_EXPLORER, _T("Project Files (*.irp)\0*.irp\0\0"),m_hWnd); if (FileDialog.DoModal() == IDOK) { // Disable the welcome screen if active. ShowWelcomePane(false); CWaitCursor WaitCursor; // This displays the hourglass cursor. if (g_ProjectManager.LoadProject(FileDialog.m_szFileName)) { // Update the view. g_TreeManager.Refresh(); lstrcpy(m_szProjectFile,FileDialog.m_szFileName); SetTitleFile(m_szProjectFile); } } return 0; } LRESULT CMainFrame::OnFileSave(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (m_szProjectFile[0] == '\0') SaveProjectAs(); else { CWaitCursor WaitCursor; // This displays the hourglass cursor. g_ProjectManager.SaveProject(m_szProjectFile); } return 0; } LRESULT CMainFrame::OnFileSaveAs(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { SaveProjectAs(); return 0; } LRESULT CMainFrame::OnShellTreeProperties(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { try { // Whether we fail or not, this message should not be processed any further. bHandled = TRUE; const HTREEITEM hSelectedItem = m_ShellTreeView.GetSelectedItem(); if (hSelectedItem == NULL) { // This command comes from the pop-up menu, which should only // come up on a selected item. ATLASSERT(false); return 0; } const CShellTreeItemInfo * const pItemInfo = (const CShellTreeItemInfo *)m_ShellTreeView.GetItemData(hSelectedItem); if (pItemInfo == NULL) { ATLASSERT(false); return 0; } SHELLEXECUTEINFO Sei; ZeroMemory(&Sei,sizeof(Sei)); Sei.cbSize= sizeof(Sei); // The MSDN documentation states the following: // With multiple monitors, if you specify an HWND // and set the lpVerb member of lpExecInfo to "Properties", // any windows created by ShellExecuteEx may not appear // in the correct position. // However, no advice is offered on how to fix this problem. // I guess we could specify the monitor to open on, // but I wouldn't be able to test such code since I only have one monitor. Sei.hwnd = m_hWnd; Sei.lpVerb = _T("properties"); // Not all shell objects have a "properties" verb, for some // of them (like the Control Panel) you'll get an error message // (even if you set the SEE_MASK_FLAG_NO_UI flag). // MSDN article "Launching Applications" explains how to look // in the Registry in order to determinate what verbs are available. // However, I don't think that's worth the effort, because // we should be displaying the full shell context menu // with CDefFolderMenu_Create2() instead, and all efforts should be // channelled to that end. Sei.fMask = SEE_MASK_INVOKEIDLIST; Sei.lpIDList = pItemInfo->pidlFullyQual; if (TRUE != ShellExecuteEx(&Sei)) { // ShellExecuteEx seems to display its own Messagebox on error, // and apparently we never come here. // I tried SEE_MASK_FLAG_NO_UI and it had no effect, // and other people have also reported that this flag // does not seem to work. ckcore::throw_from_hresult(GetLastError(),_T("ShellExecuteEx: ")); } } catch (const std::exception &e) { ATLVERIFY(IDOK == MessageBox(ckcore::get_except_msg(e).c_str(), lngGetString(GENERAL_ERROR), MB_OK | MB_ICONERROR)); } return 0; } LRESULT CMainFrame::OnFileProjectproperties(WORD wNotifyCode,WORD wID, HWND hWndCtl,BOOL &bHandled) { CProjectPropDlg ProjectPropDlg; if (ProjectPropDlg.DoModal() == IDOK) { if (g_ProjectManager.GetViewType() == PROJECTVIEWTYPE_AUDIO) { // Force the list view to redraw. m_ProjectListView.ForceRedraw(); } // Update the label. g_ProjectManager.SetDiscLabel(g_ProjectSettings.m_szLabel); g_ProjectManager.SetModified(true); } return 0; } LRESULT CMainFrame::OnFileExit(WORD wNotifyCode,WORD wID,HWND hWndCtl, BOOL &bHandled) { PostMessage(WM_CLOSE); return 0; } LRESULT CMainFrame::OnAdd(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CWaitCursor WaitCursor; // This displays the hourglass cursor. CIDA *pData = m_pShellListView->BeginGetItems(wID == ID_ADD_SELECTED); if (pData == NULL) return 0; // Prepare a project file transaction. CProjectManager::CFileTransaction Transaction; TCHAR szFileName[MAX_PATH]; IShellFolder *pParentFolder = m_pShellListView->GetParentShellFolder(); for (unsigned int i = 0; i < pData->cidl; i++) { char *pcData = reinterpret_cast(pData) + pData->aoffset[1 + i]; LPCITEMIDLIST pidl = (LPITEMIDLIST)pcData; DWORD dwAttribs = SFGAO_FILESYSTEM; if (pParentFolder->GetAttributesOf(1,&pidl,&dwAttribs) == NOERROR) { // We're not interested in non filesystem objects like the recycle bin and my computer. if (dwAttribs & SFGAO_FILESYSTEM) { m_PidlHelp.GetPathName(pParentFolder,pidl,szFileName,MAX_PATH - 1); Transaction.AddFile(szFileName); } } } m_pShellListView->EndGetItems(); return 0; } LRESULT CMainFrame::OnImport(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { WTL::CFileDialog FileDialog(true,0,0,OFN_FILEMUSTEXIST | OFN_EXPLORER, _T("File List (*.txt,*.m3u)\0*.txt;*.m3u\0\0"),m_hWnd); if (FileDialog.DoModal() == IDOK) { CWaitCursor WaitCursor; // This displays the hourglass cursor. if (!g_ProjectManager.Import(FileDialog.m_szFileName)) lngMessageBox(m_hWnd,ERROR_PROJECT_IMPORT,GENERAL_ERROR,MB_OK | MB_ICONERROR); } return 0; } LRESULT CMainFrame::OnSelectAll(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Get the focused list view control. HWND hWndListView; if (::GetFocus() == m_pShellListView->GetListViewHandle()) hWndListView = m_pShellListView->GetListViewHandle(); else hWndListView = m_ProjectListView; // Select all items in the list view. LVITEM lvItem = { 0 }; lvItem.state = LVIS_SELECTED; lvItem.stateMask = LVIS_SELECTED; for (int i = 0; i < (int)::SendMessage(hWndListView,LVM_GETITEMCOUNT,0,0L); i++) ::SendMessage(hWndListView,LVM_SETITEMSTATE,i,(LPARAM)&lvItem); return 0; } LRESULT CMainFrame::OnInvertSel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Get the focused list view control. HWND hWndListView; if (::GetFocus() == m_pShellListView->GetListViewHandle()) hWndListView = m_pShellListView->GetListViewHandle(); else hWndListView = m_ProjectListView; // Invert the selection. LVITEM lvItem = { 0 }; lvItem.state = LVIS_SELECTED; lvItem.stateMask = LVIS_SELECTED; for (int i = 0; i < (int)::SendMessage(hWndListView,LVM_GETITEMCOUNT,0,0L); i++) { lvItem.state = ::SendMessage(hWndListView,LVM_GETITEMSTATE, i,(LPARAM)LVIS_SELECTED)? 0 : LVIS_SELECTED; ::SendMessage(hWndListView,LVM_SETITEMSTATE,i,(LPARAM)&lvItem); } return 0; } LRESULT CMainFrame::OnBurncompilationCompactdisc(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_ActionManager.BurnCompilation(m_hWnd,false); return 0; } LRESULT CMainFrame::OnBurncompilationDiscimage(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Mixed mode projects can only produce disc images of the data section. if (g_ProjectManager.GetProjectType() == PROJECTTYPE_MIXED) { if (lngMessageBox(m_hWnd,CONFIRM_CREATEMIXIMAGE,GENERAL_QUESTION,MB_YESNO | MB_ICONQUESTION) == IDNO) return 0; } // Check the validity of projects using the DVD-Video file system. if (g_ProjectSettings.m_iFileSystem == FILESYSTEM_DVDVIDEO && !g_TreeManager.GetNodeFromPath(_T("/VIDEO_TS/VIDEO_TS.IFO"))) { if (lngMessageBox(m_hWnd,WARNING_BAD_DVDVIDEO,GENERAL_WARNING,MB_YESNO | MB_ICONWARNING) == IDNO) return 0; } // Check that the project is not empty. if (g_ProjectManager.IsEmpty()) { if (lngMessageBox(m_hWnd,WARNING_EMPTY_PROJECT,GENERAL_WARNING,MB_YESNO | MB_ICONWARNING) == IDNO) return 0; } g_ActionManager.CreateImage(m_hWnd,false); return 0; } LRESULT CMainFrame::OnActionsBurnimage(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_ActionManager.BurnImage(m_hWnd,false); return 0; } LRESULT CMainFrame::OnCopydiscCompactdisc(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_ActionManager.CopyDisc(m_hWnd,false); return 0; } LRESULT CMainFrame::OnCopydiscDiscimage(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_ActionManager.CopyImage(m_hWnd,false); return 0; } LRESULT CMainFrame::OnActionsManagetracks(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_ActionManager.ManageTracks(false); return 0; } LRESULT CMainFrame::OnActionsErasere(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_ActionManager.Erase(m_hWnd,false); return 0; } LRESULT CMainFrame::OnActionsFixatedisc(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_ActionManager.Fixate(m_hWnd,false); return 0; } LRESULT CMainFrame::OnActionsDiscInfo(UINT uNotifyCode,int nID,CWindow wnd) { // GetVolumeInformation() [see below] can take some time. CWaitCursor WaitCursor; // This displays the hourglass cursor. ckmmc::Device *pDevice = m_DriveMenuDeviceMap[nID - MENU_DISCINFO_IDBASE]; TCHAR szDriveLetter[4]; szDriveLetter[0] = pDevice->address().device_[0]; szDriveLetter[1] = ':'; szDriveLetter[2] = '\\'; szDriveLetter[3] = '\0'; TCHAR szTitle[128]; lstrcpy(szTitle,lngGetString(PROPERTIES_TITLE)); // Get disc label. TCHAR szDiscLabel[64]; szDiscLabel[0] = '\0'; GetVolumeInformation(szDriveLetter,szDiscLabel,63,NULL,NULL,0,NULL,0); // Include the drive letter. if (szDiscLabel[0] != '\0') { lstrcat(szTitle,szDiscLabel); lstrcat(szTitle,_T(" (X:)")); szTitle[lstrlen(szTitle) - 3] = szDriveLetter[0]; } else { lstrcat(szTitle,_T("X:")); szTitle[lstrlen(szTitle) - 2] = szDriveLetter[0]; } CDiscDlg DiscDlg(szTitle,szDiscLabel,*pDevice); DiscDlg.DoModal(); return 0; } LRESULT CMainFrame::OnActionsImportsession(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_pLogDlg->print_line(_T("CMainFrame::OnActionsImportsession")); // We can only import to projects containing a data track. CProjectNode *pDataRootNode = NULL; switch (g_ProjectManager.GetProjectType()) { case PROJECTTYPE_DATA: pDataRootNode = g_TreeManager.GetRootNode(); break; case PROJECTTYPE_MIXED: pDataRootNode = g_ProjectManager.GetMixDataRootNode(); break; //case PROJECTTYPE_AUDIO: default: return 0; } if (g_ProjectSettings.m_iFileSystem != FILESYSTEM_ISO) { if (lngMessageBox(m_hWnd,WARNING_IMPORTFS,GENERAL_WARNING,MB_YESNO | MB_ICONWARNING) == IDYES) g_ProjectSettings.m_iFileSystem = FILESYSTEM_ISO; else return 0; } CImportSessionDlg ImportSessionDlg; if (ImportSessionDlg.DoModal() == IDOK) { // Remove any previously imported sessions. g_ProjectManager.DeleteImportedItems(); // Make sure a valid track was selected. if (ImportSessionDlg.m_pSelTrackData == NULL) { g_pLogDlg->print_line(_T(" Error: Invalid track selection in import session dialog.")); return 0; } // Import the new session. ckmmc::Device *pDevice = ImportSessionDlg.m_pSelDevice; ATLASSERT(pDevice != NULL); CCore2Info Info; CCore2TrackInfo TrackInfo; if (!Info.ReadTrackInformation(*pDevice,CCore2Info::TIT_TRACK,0xFF,&TrackInfo)) { g_pLogDlg->print_line(_T(" Error: Failed to read track information when trying to import session.")); return 0; } // Import file tree. CCore2InStream InStream(g_pLogDlg,*pDevice,0, ImportSessionDlg.m_pSelTrackData->m_ulTrackAddr + ImportSessionDlg.m_pSelTrackData->m_ulTrackLen); ckfilesystem::IsoReader Reader(*g_pLogDlg); Reader.read(InStream,ImportSessionDlg.m_pSelTrackData->m_ulTrackAddr); //Reader.PrintTree(); g_TreeManager.ImportIsoTree(Reader.get_root(),pDataRootNode); g_TreeManager.Refresh(); // Update the space meter. m_SpaceMeter.SetAllocatedSize(ImportSessionDlg.m_uiAllocatedSize); // Update the (internal) project settings. g_ProjectSettings.m_bMultiSession = true; g_ProjectSettings.m_uiImportTrackAddr = ImportSessionDlg.m_pSelTrackData->m_ulTrackAddr; g_ProjectSettings.m_uiImportTrackLen = ImportSessionDlg.m_pSelTrackData->m_ulTrackLen; g_ProjectSettings.m_uiNextWritableAddr = TrackInfo.m_ulNextWritableAddr; g_ProjectSettings.m_pDevice = ImportSessionDlg.m_pSelDevice; g_ProjectSettings.m_iIsoFormat = 1; // Mode 2 (multi-session) g_pLogDlg->print_line(_T(" Imported session: %I64d-%I64d, %I64d."), g_ProjectSettings.m_uiImportTrackAddr, g_ProjectSettings.m_uiImportTrackAddr + g_ProjectSettings.m_uiImportTrackLen, g_ProjectSettings.m_uiNextWritableAddr); } return 0; } LRESULT CMainFrame::OnActionsEjectDisc(UINT uNotifyCode,int nID,CWindow wnd) { ckmmc::Device *pDevice = m_DriveMenuDeviceMap[nID - MENU_EJECTDISC_IDBASE]; if (!g_Core.EjectDisc(*pDevice,false)) lngMessageBox(HWND_DESKTOP,FAILURE_CDRTOOLS,GENERAL_ERROR,MB_OK | MB_ICONERROR); return 0; } LRESULT CMainFrame::OnViewToolBar(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_DynamicSettings.m_bViewToolBar = !g_DynamicSettings.m_bViewToolBar; ::SendMessage(m_hWndToolBar,RB_SHOWBAND, ::SendMessage(m_hWndToolBar,RB_IDTOINDEX,REBAR_TOOLBAR_ID,0), g_DynamicSettings.m_bViewToolBar); UISetCheck(ID_VIEW_STANDARDTOOLBAR,g_DynamicSettings.m_bViewToolBar); UpdateLayout(); return 0; } LRESULT CMainFrame::OnViewTBCustomize(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_ToolBarManager.Customize(); // Update the height of the toolbar band. int iBandIndex = (int)::SendMessage(m_hWndToolBar,RB_IDTOINDEX,REBAR_TOOLBAR_ID,0); if (iBandIndex != -1) { REBARBANDINFO rbInfo; rbInfo.cbSize = sizeof(REBARBANDINFO); rbInfo.fMask = RBBIM_CHILDSIZE; if (::SendMessage(m_hWndToolBar,RB_GETBANDINFO,(WPARAM)iBandIndex,(LPARAM)&rbInfo) != 0) { RECT rcToolBar; m_ToolBar.GetClientRect(&rcToolBar); rbInfo.cyMinChild = rcToolBar.bottom - rcToolBar.top; ::SendMessage(m_hWndToolBar,RB_SETBANDINFO,(WPARAM)iBandIndex,(LPARAM)&rbInfo); } } return 0; } LRESULT CMainFrame::OnViewStatusBar(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_DynamicSettings.m_bViewStatusBar = !g_DynamicSettings.m_bViewStatusBar; ::ShowWindow(m_hWndStatusBar,g_DynamicSettings.m_bViewStatusBar ? SW_SHOWNOACTIVATE : SW_HIDE); UISetCheck(ID_VIEW_STATUS_BAR,g_DynamicSettings.m_bViewStatusBar); UpdateLayout(); return 0; } LRESULT CMainFrame::OnViewProgramlog(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_pLogDlg->Show(); return 0; } LRESULT CMainFrame::OnUpLevel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Check which up level button that was clicked. if (hWndCtl == m_ProjectListViewContainer) { HTREEITEM hParent = m_ProjectTreeView.GetParentItem(m_ProjectTreeView.GetSelectedItem()); if (hParent != NULL) m_ProjectTreeView.SelectItem(hParent); } else if (hWndCtl == m_ShellListViewContainer) { HTREEITEM hParent = m_ShellTreeView.GetParentItem(m_ShellTreeView.GetSelectedItem()); if (hParent != NULL) m_ShellTreeView.SelectItem(hParent); } return 0; } LRESULT CMainFrame::OnOptionsConfiguration(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CConfigDlg ConfigDlg; ConfigDlg.DoModal(); return 0; } LRESULT CMainFrame::OnOptionsDevices(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CDevicesDlg DevicesDlg; DevicesDlg.DoModal(); return 0; } LRESULT CMainFrame::OnHelpHelptopics(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/infra_recorder/introduction.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); return 0; } LRESULT CMainFrame::OnAppAbout(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { g_pAboutWnd->CreateAndShow(m_hWnd); return 0; } LRESULT CMainFrame::OnShellPaste(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CWaitCursor WaitCursor; // This displays the hourglass cursor. if (OpenClipboard()) { if (IsClipboardFormatAvailable(CF_HDROP)) { HDROP hDrop = (HDROP)GetClipboardData(CF_HDROP); if (hDrop != NULL) { // Prepare a project file transaction. CProjectManager::CFileTransaction Transaction; unsigned int uiNumFiles = ::DragQueryFile(hDrop,0xFFFFFFFF,NULL,NULL); TCHAR szFullName[MAX_PATH]; for (unsigned int i = 0; i < uiNumFiles; i++) { if (DragQueryFile(hDrop,i,szFullName,MAX_PATH - 1)) Transaction.AddFile(szFullName); } } } CloseClipboard(); } return 0; } ================================================ FILE: src/app/dialog/main_frm.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include // COMMAND_RANGE_HANDLER_EX #include "main_view.hh" #include "space_meter.hh" #include "project_tree_view_ctrl.hh" #include "project_list_view_ctrl.hh" #include "custom_container.hh" #include "label_container.hh" #include "project_manager.hh" #include "pidl_helper.hh" #include "shell_list_view_ctrl.hh" #include "ctrl_messages.hh" #include "directory_monitor.hh" #include "custom_header_ctrl.hh" #include "toolbar_manager.hh" #include "custom_toolbar_ctrl.hh" #include "mini_html_ctrl.hh" #include "settings.hh" #include "welcome_pane.hh" // HACK: Enable doublebuffering on XP systems. #if (_WIN32_WINNT < 0x501) #define LVS_EX_DOUBLEBUFFER 0x00010000 #endif #if (WINVER < 0x0500) #define MIIM_FTYPE 0x00000100 #endif // Specified the height of the spacemeter. #define MAINFRAME_SPACEMETER_HEIGHT 30 // Specifies the index of certain menu items. #define MENU_ACTIONS_INDEX 2 #define MENU_VIEW_INDEX 3 #define MENU_DISCINFO_INDEX 8 #define MENU_EJECTDISC_INDEX 11 #define MENU_TOOLBARS_INDEX 0 // Specifies which ID the first menu item will have, the second will have + 1 and so on. #define MENU_DISCINFO_IDBASE 1000 #define MENU_EJECTDISC_IDBASE 2000 #define MENU_DRIVEMENU_MAX 128 #define PROJECTTREE_IMAGEINDEX_FOLDER 0 #define PROJECTTREE_IMAGEINDEX_DATA 1 #define PROJECTTREE_IMAGEINDEX_AUDIO 2 #define PROJECTTREE_IMAGEINDEX_MIXED 3 #define PROJECTTREE_IAMGEINDEX_DVDVIDEO 4 // Tool bar IDs. #define REBAR_MENUBAR_ID 1 #define REBAR_TOOLBAR_ID 2 // Data structure of each node in the shell tree. class CShellTreeItemInfo { public: CShellTreeItemInfo() { memset(this,0,sizeof(CShellTreeItemInfo)); } LPITEMIDLIST pidlSelf; LPITEMIDLIST pidlFullyQual; IShellFolder *pParentFolder; DWORD dwFlags; }; class CMainFrame : public CFrameWindowImpl, public CUpdateUI, public CMessageFilter, public CIdleHandler { private: HIMAGELIST m_hMainSmallImageList; HIMAGELIST m_hMainLargeImageList; HIMAGELIST m_hMiniToolBarImageList; CCommandBarCtrl m_CmdBar; CCustomToolBarCtrl m_ToolBar; CHorSplitterWindow m_SpaceMeterView; CMainView m_MainView; CSplitterWindow m_ExplorerView; CSplitterWindow m_ProjectView; CSpaceMeter m_SpaceMeter; CProjectTreeViewCtrl m_ProjectTreeView; CWelcomePane m_WelcomePane; CCustomContainer m_ProjectListViewContainer; CLabelContainer m_ProjectTreeViewContainer; CCustomContainer m_ShellListViewContainer; CLabelContainer m_ShellTreeViewContainer; CCustomHeaderCtrl m_ProjectListViewHeader; HIMAGELIST m_hProjectTreeImageList; CDirectoryMonitor m_DirectoryMonitor; CShellListViewCtrl *m_pShellListView; CTreeViewCtrlEx m_ShellTreeView; // If set to false all accelerators will be disabled. bool m_bEnableAccel; // Uses to keep track of the device index (in the device manager) from the // drive menus. For some reason it's not possible to retrieve the data member // of a menu item when it has been clicked on. ckmmc::Device *m_DriveMenuDeviceMap[MENU_DRIVEMENU_MAX]; // Is set to true if changing the tree selection is allowed. bool m_bEnableTreeSelection; //void AutoRunCheck(); bool m_bEnableAutoRun; bool EnableAutoRun(bool bEnable); // Set to true if the welcome pane is currently active. bool m_bWelcomePane; HWND CreateToolBarCtrl(); int GetDefaultMedia(); void InitializeMainSmallImageList(); void InitializeMiniToolBarImageList(); void InitializeMainView(); bool InitializeShellTreeView(); void InitializeExplorerView(unsigned int uiSplitterPos); void InitializeProjectView(unsigned int uiSplitterPos); void InitializeProjectImageLists(); bool Translate(); void FillDriveMenus(); void SetTitleFile(const TCHAR *szFullName); void SetTitleNormal(); bool SaveProjectAs(); bool SaveProjectPrompt(); // Shell related. bool OpenSpecialFolder(int iFolder); bool OpenFolder(TCHAR *szFullPath,HTREEITEM hFrom,bool bExpandMyComp); bool EnumTreeObjects(HTREEITEM hParentItem,IShellFolder *pParentFolder, LPITEMIDLIST pidlParent); bool AddFolder(TCHAR *szFullPath); bool RemoveFolder(LPITEMIDLIST pidlFullyQual); bool RenameFolder(LPITEMIDLIST pidlOldFullyQual,LPITEMIDLIST pidlNewFullyQual); bool MoveFolder(LPITEMIDLIST pidlFullyQual,TCHAR *szNewName); bool ItemExist(HTREEITEM hParentItem,LPITEMIDLIST pidl); HTREEITEM FindItemFromPath(LPITEMIDLIST pidl); void DisplayContextMenuOnShellTree(POINT ptPos,bool bWasWithKeyboard); public: DECLARE_FRAME_WND_CLASS(NULL,IDR_MAINFRAME) CMainFrame(); ~CMainFrame(); // FIXME: This is damn ugly. int m_iDefaultProjType; int m_iDefaultMedia; bool m_bDefaultProjDVDVideo; bool m_bDefaultWizard; TCHAR m_szProjectFile[MAX_PATH]; // Public controls. CProjectListViewCtrl m_ProjectListView; HMENU m_hProjListSelMenu; HMENU m_hProjListNoSelMenu; CMenu m_ShellTreeMenu; // PIDL helper object. CPidlHelper m_PidlHelp; private: virtual BOOL PreTranslateMessage(MSG *pMsg) { if (!m_bEnableAccel) return FALSE; if (CFrameWindowImpl::PreTranslateMessage(pMsg)) return TRUE; // Let the shell list view control enter keys sent to it. /*if (pMsg->hwnd == m_pShellListView->GetListViewHandle() && (pMsg->message == WM_KEYDOWN && pMsg->wParam == VK_RETURN)) { return FALSE; } return IsDialogMessage(pMsg);*/ // Let the IsDialogMessage function process tab keys so it can help us // tab between controls. if (pMsg->message == WM_KEYDOWN && pMsg->wParam == VK_TAB) { return IsDialogMessage(pMsg); } return FALSE; } virtual BOOL OnIdle() { UIUpdateToolBar(); return FALSE; } public: void ShowWelcomePane(bool bShow) { m_bWelcomePane = bShow; if (bShow) { m_SpaceMeterView.SetSplitterPane(SPLIT_PANE_TOP,m_WelcomePane); m_SpaceMeterView.SetSinglePaneMode(SPLIT_PANE_TOP); } else { m_SpaceMeterView.SetSinglePaneMode(); m_SpaceMeterView.SetSplitterPane(SPLIT_PANE_BOTTOM,m_SpaceMeter); m_SpaceMeterView.SetSplitterPane(SPLIT_PANE_TOP,m_MainView); // Setup splitters. RECT rcClient; ::GetClientRect(m_hWndClient,&rcClient); m_SpaceMeterView.SetSplitterPos(rcClient.bottom - rcClient.top - MAINFRAME_SPACEMETER_HEIGHT); m_MainView.SetSplitterPos((rcClient.bottom - rcClient.top - MAINFRAME_SPACEMETER_HEIGHT)/2); int iSplitterPos = (rcClient.right - rcClient.left) / 4; m_ExplorerView.SetSplitterPos(iSplitterPos); m_ProjectView.SetSplitterPos(iSplitterPos); WINDOWPLACEMENT wp; GetWindowPlacement(&wp); if (wp.showCmd != SW_MAXIMIZE) { // Load the last used window position and size. if (g_DynamicSettings.m_rcWindow.left != -1 && g_DynamicSettings.m_rcWindow.right != -1 && g_DynamicSettings.m_rcWindow.top != -1 && g_DynamicSettings.m_rcWindow.bottom != -1) { SetWindowPos(HWND_TOP,&g_DynamicSettings.m_rcWindow,0); } else { GetWindowRect(&g_DynamicSettings.m_rcWindow); g_DynamicSettings.m_rcWindow.right += 300; g_DynamicSettings.m_rcWindow.bottom += 200; SetWindowPos(HWND_TOP,&g_DynamicSettings.m_rcWindow,0); } } } } BEGIN_UPDATE_UI_MAP(CMainFrame) // Edit menu. UPDATE_ELEMENT(ID_EDIT_NEWFOLDER,UPDUI_MENUPOPUP) UPDATE_ELEMENT(ID_EDIT_RENAME,UPDUI_MENUPOPUP) UPDATE_ELEMENT(ID_EDIT_REMOVE,UPDUI_MENUPOPUP) // Actions menu. UPDATE_ELEMENT(ID_BURNCOMPILATION_DISCIMAGE,UPDUI_MENUPOPUP) UPDATE_ELEMENT(ID_ACTIONS_IMPORTSESSION,UPDUI_MENUPOPUP) // View menu. UPDATE_ELEMENT(ID_VIEW_STANDARDTOOLBAR,UPDUI_MENUPOPUP) UPDATE_ELEMENT(ID_VIEW_STATUS_BAR,UPDUI_MENUPOPUP) UPDATE_ELEMENT(ID_VIEW_LARGEICONS,UPDUI_MENUPOPUP) UPDATE_ELEMENT(ID_VIEW_SMALLICONS,UPDUI_MENUPOPUP) UPDATE_ELEMENT(ID_VIEW_LIST,UPDUI_MENUPOPUP) UPDATE_ELEMENT(ID_VIEW_DETAILS,UPDUI_MENUPOPUP) END_UPDATE_UI_MAP() private: #if _ATL_VER <= 0x0300 BEGIN_MSG_MAP_EX(CMainFrame) #else BEGIN_MSG_MAP(CMainFrame) #endif MESSAGE_HANDLER(WM_CREATE,OnCreate) MESSAGE_HANDLER(WM_DESTROY,OnDestroy) MESSAGE_HANDLER(WM_CLOSE,OnClose) MESSAGE_HANDLER(WM_SHELLCHANGE,OnShellChange) MESSAGE_HANDLER(WM_GETISHELLBROWSER,OnGetIShellBrowser) MESSAGE_HANDLER(WM_CONTEXTMENU,OnContextMenu) MESSAGE_HANDLER(WM_DEVICECHANGE,OnDeviceChange) // Shell list view. MESSAGE_HANDLER(WM_SLVC_BROWSEOBJECT,OnSLVBrowseObject) MESSAGE_HANDLER(WM_SLVC_DONEBROWSEOBJECT,OnSLVDoneBrowseObject) MESSAGE_HANDLER(WM_SLVC_CHANGEFOLDER,OnSLVChangeFolder) MESSAGE_HANDLER(WM_SLVC_CHANGEFOLDERLINK,OnSLVChangeFolderLink) // Shell tree view. NOTIFY_HANDLER(IDC_SHELLTREEVIEW,TVN_GETDISPINFO,OnSTVGetDispInfo) NOTIFY_HANDLER(IDC_SHELLTREEVIEW,TVN_ITEMEXPANDING,OnSTVItemExpanding) NOTIFY_HANDLER(IDC_SHELLTREEVIEW,TVN_DELETEITEM,OnSTVDeleteItem) NOTIFY_HANDLER(IDC_SHELLTREEVIEW,TVN_SELCHANGED,OnSTVSelChanged) NOTIFY_HANDLER(IDC_SHELLTREEVIEW,TVN_BEGINDRAG,OnSTVBeginDrag) NOTIFY_HANDLER(IDC_SHELLTREEVIEW,NM_RCLICK,OnSTVRClick) // Project tree view. NOTIFY_HANDLER(IDC_PROJECTTREEVIEW,TVN_GETDISPINFO,OnPTVGetDispInfo) NOTIFY_HANDLER(IDC_PROJECTTREEVIEW,TVN_SELCHANGING,OnPTVSelChanging) NOTIFY_HANDLER(IDC_PROJECTTREEVIEW,TVN_SELCHANGED,OnPTVSelChanged) NOTIFY_HANDLER(IDC_PROJECTTREEVIEW,TVN_BEGINLABELEDIT,OnPTVBeginLabelEdit) NOTIFY_HANDLER(IDC_PROJECTTREEVIEW,TVN_ENDLABELEDIT,OnPTVEndLabelEdit) NOTIFY_HANDLER(IDC_PROJECTTREEVIEW,TVN_BEGINDRAG,OnPTVBeginDrag) NOTIFY_HANDLER(IDC_PROJECTTREEVIEW,NM_RCLICK,OnPTVRClick) // Project list view. NOTIFY_HANDLER(IDC_PROJECTLISTVIEW,LVN_GETDISPINFO,OnPLVGetDispInfo) NOTIFY_HANDLER(IDC_PROJECTLISTVIEW,LVN_BEGINLABELEDIT,OnPLVBeginLabelEdit) NOTIFY_HANDLER(IDC_PROJECTLISTVIEW,LVN_ENDLABELEDIT,OnPLVEndLabelEdit) NOTIFY_HANDLER(IDC_PROJECTLISTVIEW,NM_DBLCLK,OnPLVDblClk) NOTIFY_HANDLER(IDC_PROJECTLISTVIEW,NM_RCLICK,OnPLVRClick) NOTIFY_HANDLER(IDC_PROJECTLISTVIEW,LVN_ITEMCHANGED,OnPLVItemChanged) NOTIFY_HANDLER(IDC_PROJECTLISTVIEW,LVN_DELETEITEM,OnPLVDeleteItem) NOTIFY_HANDLER(IDC_PROJECTLISTVIEW,LVN_BEGINDRAG,OnPLVBeginDrag) NOTIFY_HANDLER(IDC_PROJECTLISTVIEW,LVN_COLUMNCLICK,OnPLVColumnClick) // Toolbar. NOTIFY_HANDLER(ATL_IDW_TOOLBAR,TBN_BEGINADJUST,g_ToolBarManager.OnToolBarBeginAdjust) NOTIFY_HANDLER(ATL_IDW_TOOLBAR,TBN_INITCUSTOMIZE,g_ToolBarManager.OnToolBarInitCustomize) NOTIFY_HANDLER(ATL_IDW_TOOLBAR,TBN_QUERYINSERT,g_ToolBarManager.OnToolBarQueryInsert) NOTIFY_HANDLER(ATL_IDW_TOOLBAR,TBN_QUERYDELETE,g_ToolBarManager.OnToolBarQueryDelete) NOTIFY_HANDLER(ATL_IDW_TOOLBAR,TBN_GETBUTTONINFO,g_ToolBarManager.OnToolBarGetButtonInfo) NOTIFY_HANDLER(ATL_IDW_TOOLBAR,TBN_RESET,g_ToolBarManager.OnToolBarReset) // For translation purposes. NOTIFY_CODE_HANDLER(TTN_GETDISPINFO,OnToolTipGetInfo) MESSAGE_HANDLER(WM_MENUSELECT,OnMenuSelect) // File menu. COMMAND_ID_HANDLER(ID_NEWPROJECT_DATACD,OnNewProjectDataCD) COMMAND_ID_HANDLER(ID_NEWPROJECT_DATACDMS,OnNewProjectDataCDMS) COMMAND_ID_HANDLER(ID_NEWPROJECT_DATADVD,OnNewProjectDataDVD) COMMAND_ID_HANDLER(ID_NEWPROJECT_AUDIO,OnNewProjectAudio) COMMAND_ID_HANDLER(ID_NEWPROJECT_MIXED,OnNewProjectMixed) COMMAND_ID_HANDLER(ID_NEWPROJECT_DVDVIDEO,OnNewProjectDVDVideo) COMMAND_ID_HANDLER(ID_FILE_OPEN,OnFileOpen) COMMAND_ID_HANDLER(ID_FILE_SAVE,OnFileSave) COMMAND_ID_HANDLER(ID_FILE_SAVE_AS,OnFileSaveAs) COMMAND_ID_HANDLER(ID_FILE_PROJECTPROPERTIES,OnFileProjectproperties) COMMAND_ID_HANDLER(ID_APP_EXIT,OnFileExit) // Edit menu. COMMAND_ID_HANDLER(ID_EDIT_NEWFOLDER,g_ProjectManager.OnNewFolder) COMMAND_ID_HANDLER(ID_EDIT_RENAME,g_ProjectManager.OnRename) COMMAND_ID_HANDLER(ID_EDIT_REMOVE,g_ProjectManager.OnRemove) COMMAND_ID_HANDLER(ID_ADD_SELECTED,OnAdd) COMMAND_ID_HANDLER(ID_ADD_ALL,OnAdd) COMMAND_ID_HANDLER(ID_EDIT_IMPORT,OnImport) COMMAND_ID_HANDLER(ID_EDIT_SELECTALL,OnSelectAll) COMMAND_ID_HANDLER(ID_EDIT_INVERTSELECTION,OnInvertSel) // Actions menu. COMMAND_ID_HANDLER(ID_BURNCOMPILATION_COMPACTDISC,OnBurncompilationCompactdisc) COMMAND_ID_HANDLER(ID_BURNCOMPILATION_DISCIMAGE,OnBurncompilationDiscimage) COMMAND_ID_HANDLER(ID_ACTIONS_BURNIMAGE,OnActionsBurnimage) COMMAND_ID_HANDLER(ID_COPYDISC_COMPACTDISC,OnCopydiscCompactdisc) COMMAND_ID_HANDLER(ID_COPYDISC_DISCIMAGE,OnCopydiscDiscimage) COMMAND_ID_HANDLER(ID_ACTIONS_MANAGETRACKS,OnActionsManagetracks) COMMAND_ID_HANDLER(ID_ACTIONS_ERASERE,OnActionsErasere) COMMAND_ID_HANDLER(ID_ACTIONS_FIXATEDISC,OnActionsFixatedisc) COMMAND_RANGE_HANDLER_EX(MENU_DISCINFO_IDBASE,MENU_DISCINFO_IDBASE + MENU_DRIVEMENU_MAX - 1,OnActionsDiscInfo) COMMAND_ID_HANDLER(ID_ACTIONS_IMPORTSESSION,OnActionsImportsession) COMMAND_RANGE_HANDLER_EX(MENU_EJECTDISC_IDBASE,MENU_EJECTDISC_IDBASE + MENU_DRIVEMENU_MAX - 1,OnActionsEjectDisc) // View menu. COMMAND_ID_HANDLER(ID_VIEW_STANDARDTOOLBAR,OnViewToolBar) COMMAND_ID_HANDLER(ID_VIEW_TBCUSTOMIZE,OnViewTBCustomize) COMMAND_ID_HANDLER(ID_VIEW_STATUS_BAR,OnViewStatusBar) COMMAND_ID_HANDLER(ID_VIEW_PROGRAMLOG,OnViewProgramlog) COMMAND_ID_HANDLER(ID_VIEW_LARGEICONS,m_ProjectListView.OnViewLargeIcons) COMMAND_ID_HANDLER(ID_VIEW_SMALLICONS,m_ProjectListView.OnViewSmallIcons) COMMAND_ID_HANDLER(ID_VIEW_LIST,m_ProjectListView.OnViewList) COMMAND_ID_HANDLER(ID_VIEW_DETAILS,m_ProjectListView.OnViewDetails) COMMAND_ID_HANDLER(ID_VIEW_UPLEVEL,OnUpLevel) // Options menu. COMMAND_ID_HANDLER(ID_OPTIONS_CONFIGURATION,OnOptionsConfiguration) COMMAND_ID_HANDLER(ID_OPTIONS_DEVICES,OnOptionsDevices) // Help menu. COMMAND_ID_HANDLER(ID_HELP_HELPTOPICS,OnHelpHelptopics) COMMAND_ID_HANDLER(ID_APP_ABOUT,OnAppAbout) // Shell tree popup menu. COMMAND_ID_HANDLER(ID_POPUPMENU_SHELLTREE_PROPERTIES,OnShellTreeProperties) // Project list popup menu. COMMAND_ID_HANDLER(ID_POPUPMENU_PROPERTIES,OnFileProjectproperties) // Custom. COMMAND_ID_HANDLER(ID_SHELL_PASTE,OnShellPaste) CHAIN_MSG_MAP(CUpdateUI) CHAIN_MSG_MAP(CFrameWindowImpl) END_MSG_MAP() HMENU GetToolBarsMenu(); HIMAGELIST GetToolBarSmall(); HIMAGELIST GetToolBarLarge(); LRESULT OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnDestroy(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnClose(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnShellChange(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnGetIShellBrowser(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnContextMenu(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnDeviceChange(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); // Shell list view. LRESULT OnSLVBrowseObject(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSLVDoneBrowseObject(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSLVChangeFolder(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSLVChangeFolderLink(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSTVGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnSTVItemExpanding(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnSTVDeleteItem(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnSTVSelChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnSTVBeginDrag(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnSTVRClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPTVGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPTVSelChanging(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPTVSelChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPTVBeginLabelEdit(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPTVEndLabelEdit(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPTVBeginDrag(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPTVRClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPLVGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPLVBeginLabelEdit(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPLVEndLabelEdit(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPLVDblClk(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPLVRClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPLVItemChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPLVDeleteItem(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPLVBeginDrag(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnPLVColumnClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); // For translation purposes. LRESULT OnToolTipGetInfo(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnMenuSelect(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); // File menu. LRESULT OnNewProjectDataCD(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnNewProjectDataCDMS(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnNewProjectDataDVD(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnNewProjectAudio(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnNewProjectMixed(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnNewProjectDVDVideo(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFileOpen(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFileSave(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFileSaveAs(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnShellTreeProperties(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFileProjectproperties(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnFileExit(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); // Edit menu. LRESULT OnAdd(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnImport(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnSelectAll(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnInvertSel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); // Actions menu. LRESULT OnBurncompilationCompactdisc(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnBurncompilationDiscimage(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnActionsBurnimage(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCopydiscCompactdisc(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCopydiscDiscimage(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnActionsManagetracks(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnActionsErasere(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnActionsFixatedisc(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnActionsDiscInfo(UINT uNotifyCode,int nID,CWindow wnd); LRESULT OnActionsImportsession(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnActionsEjectDisc(UINT uNotifyCode,int nID,CWindow wnd); // View menu. LRESULT OnViewToolBar(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnViewTBCustomize(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnViewStatusBar(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnViewProgramlog(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnUpLevel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); // Options menu. LRESULT OnOptionsConfiguration(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnOptionsDevices(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); // Help menu. LRESULT OnHelpHelptopics(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnAppAbout(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); // Custom. LRESULT OnShellPaste(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; extern CMainFrame *g_pMainFrame; ================================================ FILE: src/app/dialog/main_view.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "visual_styles.hh" #include "resource.h" #include "main_view.hh" CMainView::CMainView() : m_uiBorderSize(MAINVIEW_THEMEDBORDER_SIZE), m_bHintBar(false),m_HintType(HT_INFORMATION), m_ButtonState(BS_NORMAL), m_hIconImageList(NULL),m_hCloseImageList(NULL) { // Fill the icon image list. m_hIconImageList = ImageList_Create(16,16,ILC_COLOR32,0,4); ImageList_AddIcon(m_hIconImageList,LoadIcon(NULL,IDI_INFORMATION)); ImageList_AddIcon(m_hIconImageList,LoadIcon(NULL,IDI_WARNING)); ImageList_AddIcon(m_hIconImageList,LoadIcon(NULL,IDI_ERROR)); ImageList_AddIcon(m_hIconImageList,LoadIcon(NULL,IDI_WINLOGO)); // Fill the close image list. HBITMAP hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_PANECLOSEBITMAP)); m_hCloseImageList = ImageList_Create(16,16,ILC_COLOR32 | ILC_MASK,0,4); ImageList_AddMasked(m_hCloseImageList,hBitmap,RGB(255,0,255)); DeleteObject(hBitmap); } CMainView::~CMainView() { if (m_hIconImageList != NULL) ImageList_Destroy(m_hIconImageList); if (m_hCloseImageList != NULL) ImageList_Destroy(m_hCloseImageList); } LRESULT CMainView::OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // If the application is themed, we use a different border size. if (!g_VisualStyles.IsThemeActive()) m_uiBorderSize = MAINVIEW_NORMALBORDER_SIZE; return 0; } LRESULT CMainView::OnNCCalcSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { RECT *pRect = (RECT *)lParam; // Contract all size of the rectangle except for the bottom. The reason for // this is that the space meter and this view is separated by a splitter. pRect->left += m_uiBorderSize; pRect->right -= m_uiBorderSize; pRect->top += m_uiBorderSize; // Let the default window proc adjust the rect further since there might be // a scrollbar visible. //DefWindowProc(uMsg,wParam,lParam); if (m_bHintBar) pRect->top += MAINVIEW_HINTBAR_SIZE; return 0; } LRESULT CMainView::OnNCPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { RECT rcClient; // Get the window rect and convert it's origin to 0,0 instead of the top // left of the screen. GetWindowRect(&rcClient); HDC hDC = GetWindowDC(); rcClient.bottom -= rcClient.top; rcClient.top = 0; rcClient.right -= rcClient.left; rcClient.left = 0; // Since FillRect is used, the center needs to be excluded. // Otherwise there will be some flicker and drawing issues. ExcludeClipRect(hDC,rcClient.left + m_uiBorderSize, rcClient.top + m_uiBorderSize + (m_bHintBar ? MAINVIEW_HINTBAR_SIZE : 0), rcClient.right - m_uiBorderSize, rcClient.bottom); FillRect(hDC,&rcClient,GetSysColorBrush(COLOR_BTNFACE)); if (m_bHintBar) { RECT rcHintBar = rcClient; rcHintBar.bottom = rcHintBar.top + MAINVIEW_HINTBAR_SIZE; DrawHintBar(hDC,rcHintBar); } ReleaseDC(hDC); bHandled = false; return 0; } LRESULT CMainView::OnNCMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Only deal with this event if the hint bar is visible. if (!m_bHintBar) return 0; POINT ptMouse = { GET_X_LPARAM(lParam),GET_Y_LPARAM(lParam) }; RECT rcButton,rcWindow; GetWindowRect(&rcWindow); RECT rcHintBar = rcWindow; rcHintBar.bottom = rcHintBar.top + MAINVIEW_HINTBAR_SIZE; rcButton.top = rcHintBar.top + MAINVIEW_HINTBAR_SIZE/2 - 8; rcButton.right = rcHintBar.right - (MAINVIEW_HINTBAR_SIZE/2 - 8); rcButton.bottom = rcButton.top + 16; rcButton.left = rcButton.right - 16; eButtonState NewState; if (::PtInRect(&rcButton,ptMouse)) { if (m_ButtonState != BS_DOWN) NewState = BS_HOVER; else NewState = BS_DOWN; } else { NewState = BS_NORMAL; } if (NewState != m_ButtonState) { m_ButtonState = NewState; InvalidateRect(&rcButton); SetWindowPos(NULL,0,0,0,0,SWP_NOOWNERZORDER | SWP_NOSIZE | SWP_NOMOVE | SWP_DRAWFRAME); } return 0; } LRESULT CMainView::OnNCMouseDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Only deal with this event if the hint bar is visible. if (!m_bHintBar) return 0; POINT ptMouse = { GET_X_LPARAM(lParam),GET_Y_LPARAM(lParam) }; RECT rcButton,rcWindow; GetWindowRect(&rcWindow); RECT rcHintBar = rcWindow; rcHintBar.bottom = rcHintBar.top + MAINVIEW_HINTBAR_SIZE; rcButton.top = rcHintBar.top + MAINVIEW_HINTBAR_SIZE/2 - 8; rcButton.right = rcHintBar.right - (MAINVIEW_HINTBAR_SIZE/2 - 8); rcButton.bottom = rcButton.top + 16; rcButton.left = rcButton.right - 16; if (::PtInRect(&rcButton,ptMouse)) { m_ButtonState = BS_DOWN; InvalidateRect(&rcButton); SetWindowPos(NULL,0,0,0,0,SWP_NOOWNERZORDER | SWP_NOSIZE | SWP_NOMOVE | SWP_DRAWFRAME); } return 0; } LRESULT CMainView::OnNCMouseUp(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Only deal with this event if the hint bar is visible. if (!m_bHintBar) return 0; POINT ptMouse = { GET_X_LPARAM(lParam),GET_Y_LPARAM(lParam) }; RECT rcButton,rcWindow; GetWindowRect(&rcWindow); RECT rcHintBar = rcWindow; rcHintBar.bottom = rcHintBar.top + MAINVIEW_HINTBAR_SIZE; rcButton.top = rcHintBar.top + MAINVIEW_HINTBAR_SIZE/2 - 8; rcButton.right = rcHintBar.right - (MAINVIEW_HINTBAR_SIZE/2 - 8); rcButton.bottom = rcButton.top + 16; rcButton.left = rcButton.right - 16; if (::PtInRect(&rcButton,ptMouse)) { if (m_ButtonState == BS_DOWN) HideHintMsg(); m_ButtonState = BS_HOVER; InvalidateRect(&rcButton); SetWindowPos(NULL,0,0,0,0,SWP_NOOWNERZORDER | SWP_NOSIZE | SWP_NOMOVE | SWP_DRAWFRAME); } else { m_ButtonState = BS_NORMAL; InvalidateRect(&rcButton); SetWindowPos(NULL,0,0,0,0,SWP_NOOWNERZORDER | SWP_NOSIZE | SWP_NOMOVE | SWP_DRAWFRAME); } return 0; } LRESULT CMainView::OnNCHitTest(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { return HTBORDER; } void CMainView::DrawHintBar(HDC hDC,RECT &rcHintBar) { // Draw the background. FillRect(hDC,&rcHintBar,GetSysColorBrush(COLOR_INFOBK)); // Draw background highlight. RECT rcHighlight = rcHintBar; rcHighlight.bottom = rcHighlight.top + 1; FillRect(hDC,&rcHighlight,GetSysColorBrush(COLOR_WINDOW)); rcHighlight.bottom = rcHintBar.bottom; rcHighlight.right = rcHighlight.left + 1; FillRect(hDC,&rcHighlight,GetSysColorBrush(COLOR_WINDOW)); // Draw background shadow. RECT rcShadow = rcHintBar; rcShadow.top = rcShadow.bottom - 1; FillRect(hDC,&rcShadow,GetSysColorBrush(COLOR_3DLIGHT)); rcShadow.top = rcHintBar.top; rcShadow.left = rcShadow.right - 1; FillRect(hDC,&rcShadow,GetSysColorBrush(COLOR_3DLIGHT)); // Draw icon. ImageList_Draw(m_hIconImageList,static_cast(m_HintType),hDC, MAINVIEW_HINTBAR_SIZE/2 - 8, MAINVIEW_HINTBAR_SIZE/2 - 8,ILD_TRANSPARENT); // Draw the close button. ImageList_Draw(m_hCloseImageList,static_cast(m_ButtonState),hDC, rcHintBar.right - MAINVIEW_HINTBAR_SIZE/2 - 8, MAINVIEW_HINTBAR_SIZE/2 - 8,ILD_TRANSPARENT); // Draw text. RECT rcText; rcText.left = rcHintBar.left + 16 + (MAINVIEW_HINTBAR_SIZE/2 - 8) * 2; rcText.right = rcHintBar.right; rcText.top = rcHintBar.top; rcText.bottom = rcHintBar.bottom; SetBkColor(hDC,GetSysColor(COLOR_INFOBK)); SetTextColor(hDC,GetSysColor(COLOR_INFOTEXT)); HFONT hOldFont = (HFONT)SelectObject(hDC,AtlGetDefaultGuiFont()); DrawText(hDC,m_HintMsg.c_str(),static_cast(m_HintMsg.size()),&rcText, DT_LEFT | DT_END_ELLIPSIS | DT_SINGLELINE | DT_VCENTER); if (hOldFont != NULL) SelectObject(hDC,hOldFont); } void CMainView::ShowHintMsg(eHintType HintType,const TCHAR *szHintMsg) { m_bHintBar = true; m_HintType = HintType; m_HintMsg = szHintMsg; m_ButtonState = BS_NORMAL; SetWindowPos(NULL,0,0,0,0,SWP_NOOWNERZORDER | SWP_NOSIZE | SWP_NOMOVE | SWP_FRAMECHANGED); PlaySound(_T("SystemNotification"),0,SND_ASYNC | SND_ALIAS | SND_NOWAIT); } void CMainView::HideHintMsg() { m_bHintBar = false; SetWindowPos(NULL,0,0,0,0,SWP_NOOWNERZORDER | SWP_NOSIZE | SWP_NOMOVE | SWP_FRAMECHANGED); } ================================================ FILE: src/app/dialog/main_view.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #define MAINVIEW_NORMALBORDER_SIZE 2 #define MAINVIEW_THEMEDBORDER_SIZE 4 #define MAINVIEW_HINTBAR_SIZE 28 class CMainView : public CSplitterWindowImpl { public: enum eHintType { HT_INFORMATION = 0, HT_WARNING = 1, HT_ERROR = 2, HT_EXTERNAL = 3 }; private: enum eButtonState { BS_NORMAL = 0, BS_HOVER = 1, BS_DOWN = 2, BS_DISABLED = 3 }; unsigned int m_uiBorderSize; bool m_bHintBar; eHintType m_HintType; ckcore::tstring m_HintMsg; eButtonState m_ButtonState; HIMAGELIST m_hIconImageList; HIMAGELIST m_hCloseImageList; void DrawHintBar(HDC hDC,RECT &rcHintBar); public: CMainView(); ~CMainView(); typedef CSplitterWindowImpl _baseClass; BEGIN_MSG_MAP(CMainView) MESSAGE_HANDLER(WM_CREATE,OnCreate) MESSAGE_HANDLER(WM_NCCALCSIZE,OnNCCalcSize) MESSAGE_HANDLER(WM_NCPAINT,OnNCPaint) MESSAGE_HANDLER(WM_NCMOUSEMOVE,OnNCMouseMove) MESSAGE_HANDLER(WM_NCLBUTTONDOWN,OnNCMouseDown) MESSAGE_HANDLER(WM_NCLBUTTONUP,OnNCMouseUp) MESSAGE_HANDLER(WM_NCHITTEST,OnNCHitTest) CHAIN_MSG_MAP(_baseClass); END_MSG_MAP() LRESULT OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnNCCalcSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnNCPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnNCMouseMove(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnNCMouseDown(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnNCMouseUp(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnNCHitTest(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); void ShowHintMsg(eHintType HintType,const TCHAR *szHintMsg); void HideHintMsg(); }; ================================================ FILE: src/app/dialog/new_file_ext_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "new_file_ext_dlg.hh" #include #include "string_table.hh" #include "settings.hh" CNewFileExtDlg::CNewFileExtDlg() { } CNewFileExtDlg::~CNewFileExtDlg() { } bool CNewFileExtDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a newfileext translation section. if (!pLng->EnterSection(_T("newfileext"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDD_NEWFILEEXTDLG,szStrValue)) // Title. SetWindowText(szStrValue); if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDC_DESCSTATIC,szStrValue)) SetDlgItemText(IDC_DESCSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_EXTSTATIC,szStrValue)) SetDlgItemText(IDC_EXTSTATIC,szStrValue); return true; } LRESULT CNewFileExtDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); m_DescEdit.SubclassWindow(GetDlgItem(IDC_DESCEDIT)); m_ExtEdit.SubclassWindow(GetDlgItem(IDC_EXTEDIT)); m_DescEdit.SetLimitText(63); m_ExtEdit.SetLimitText(63); // Translate the window. Translate(); return TRUE; } LRESULT CNewFileExtDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { GetDlgItemText(IDC_DESCEDIT,m_szDescBuffer,63); GetDlgItemText(IDC_EXTEDIT,m_szExtBuffer,63); EndDialog(wID); return FALSE; } LRESULT CNewFileExtDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } ================================================ FILE: src/app/dialog/new_file_ext_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "custom_edit_ctrl.hh" class CNewFileExtDlg : public CDialogImpl { private: CCustomEditCtrl m_DescEdit; CCustomEditCtrl m_ExtEdit; bool Translate(); public: enum { IDD = IDD_NEWFILEEXTDLG }; TCHAR m_szDescBuffer[64]; TCHAR m_szExtBuffer[64]; CNewFileExtDlg(); ~CNewFileExtDlg(); BEGIN_MSG_MAP(CNewFileExtDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/progress_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "string_table.hh" #include "lang_util.hh" #include "settings.hh" #include "infrarecorder.hh" #include "device_util.hh" #include "version.hh" #include "progress_dlg.hh" static const int SUBITEM_TEXT = 1; CProgressDlg::CProgressDlg() : m_pProcess(NULL),m_bAppMode(false), m_bRealMode(false),m_bCancelled(false),m_hWndHost(NULL),m_ucPercent(0), m_szHostTitle(NULL),m_pFlashWindowEx(NULL),m_bNeedToFocusOkButton(false) { // Load the icons. m_hListImageList = ImageList_Create(16,16,ILC_COLOR32,0,4); ImageList_AddIcon(m_hListImageList,LoadIcon(NULL,IDI_INFORMATION)); ImageList_AddIcon(m_hListImageList,LoadIcon(NULL,IDI_WARNING)); ImageList_AddIcon(m_hListImageList,LoadIcon(NULL,IDI_ERROR)); ImageList_AddIcon(m_hListImageList,LoadIcon(NULL,IDI_WINLOGO)); // The MSDN documentation states that FlashWindowEx() is only // available in Windows 2000 and later. However, MS KB article ID 254339 // states that you can use this API in Windows 98 too. const HMODULE hUser32 = GetModuleHandle(_T("USER32.DLL")); if (hUser32 == NULL) { ATLASSERT(false); // This should never happen at this point. } else { m_pFlashWindowEx = (PointerToFlashWindowEx)GetProcAddress(hUser32,"FlashWindowEx"); // This should never happen at this point. ATLASSERT(m_pFlashWindowEx != NULL); } SMOKE_INIT } CProgressDlg::~CProgressDlg() { if (m_hListImageList != NULL) ImageList_Destroy(m_hListImageList); if (m_szHostTitle != NULL) { delete m_szHostTitle; m_szHostTitle = NULL; } } bool CProgressDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a progress translation section. if (!pLng->EnterSection(_T("progress"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDC_RELOADBUTTON,szStrValue)) SetDlgItemText(IDC_RELOADBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_BUFFERSTATIC,szStrValue)) SetDlgItemText(IDC_BUFFERSTATIC,szStrValue); return true; } void CProgressDlg::AttachProcess(ckcore::Process *pProcess) { m_pProcess = pProcess; } void CProgressDlg::AttachHost(HWND hWndHost) { m_hWndHost = hWndHost; } void CProgressDlg::SetAppMode(bool bAppMode) { m_bAppMode = bAppMode; } void CProgressDlg::SetRealMode(bool bRealMode) { m_bRealMode = bRealMode; } void CProgressDlg::set_progress(unsigned char ucPercent) { if (ucPercent < 0) ucPercent = 0; else if (ucPercent > 100) ucPercent = 100; // Make sure that the progress does not go in the wrong direction. if (ucPercent < m_ucPercent && ucPercent != 0) return; // Only redraw when we have to. if (m_ucPercent != ucPercent) { m_ucPercent = ucPercent; SendDlgItemMessage(IDC_TOTALPROGRESS,PBM_SETPOS,(WPARAM)ucPercent,0); TCHAR szProgress[32]; lsnprintf_s(szProgress,32,lngGetString(PROGRESS_TOTAL),ucPercent); m_TotalStatic.SetWindowText(szProgress); // Update parent title if necessary. if (!m_bAppMode && m_szHostTitle != NULL) { TCHAR szTitle[64]; GetWindowText(szTitle,sizeof(szTitle)/sizeof(TCHAR)); TCHAR szHostTitle[32 + 64]; lsnprintf_s(szHostTitle,sizeof(szHostTitle)/sizeof(TCHAR),_T("%d%% - %s"),ucPercent,szTitle); GetParentWindow(this).SetWindowText(szHostTitle); } ProcessMessages(); } } void CProgressDlg::set_marquee(bool bEnable) { // Only supported in Windows XP and newer (common controls version 6). if (g_WinVer.m_ulMajorCCVersion >= 6) { HWND hWndCtrl = GetDlgItem(IDC_TOTALPROGRESS); if (bEnable) { unsigned long ulStyle = ::GetWindowLong(hWndCtrl,GWL_STYLE); ::SetWindowLong(hWndCtrl,GWL_STYLE,ulStyle | PBS_MARQUEE); ::SendMessage(hWndCtrl,PBM_SETMARQUEE,TRUE,50); } else { unsigned long ulStyle = ::GetWindowLong(hWndCtrl,GWL_STYLE); ::SetWindowLong(hWndCtrl,GWL_STYLE,ulStyle & ~PBS_MARQUEE); ::SendMessage(hWndCtrl,PBM_SETMARQUEE,FALSE,50); } } } void CProgressDlg::set_status(const TCHAR *szStatus,...) { // Prepare the string. TCHAR szStatusStr[256]; lstrcpy(szStatusStr,lngGetString(PROGRESS_STATUS)); unsigned int uiFreeSpace = sizeof(szStatusStr)/sizeof(TCHAR) - lstrlen(szStatusStr) - 1; if ((unsigned int)lstrlen(szStatus) > uiFreeSpace) lstrncat(szStatusStr,szStatus,uiFreeSpace); else lstrcat(szStatusStr,szStatus); // Parse the variable argument list. va_list args; va_start(args,szStatus); _vsnwprintf(m_szStringBuffer,PROGRESS_STRINGBUFFER_SIZE - 1,szStatusStr,args); m_StatusStatic.SetWindowText(m_szStringBuffer); } void CProgressDlg::notify(ckcore::Progress::MessageType Type,const TCHAR *szMessage,...) { int iItemIndex = m_ListView.GetItemCount(); // Time. SYSTEMTIME st; GetLocalTime(&st); TCHAR szTime[9]; // xx:yy:zz lsprintf(szTime,_T("%.2d:%.2d:%.2d"),st.wHour,st.wMinute,st.wSecond); szTime[8] = '\0'; // Convert the log type to an index. int iImageIndex = 0; switch (Type) { case ckcore::Progress::ckINFORMATION: iImageIndex = 0; break; case ckcore::Progress::ckWARNING: iImageIndex = 1; break; case ckcore::Progress::ckERROR: iImageIndex = 2; break; case ckcore::Progress::ckEXTERNAL: iImageIndex = 3; break; } m_ListView.AddItem(iItemIndex,0,szTime,iImageIndex); // Parse the variable argument list. va_list args; va_start(args,szMessage); _vsnwprintf(m_szStringBuffer,PROGRESS_STRINGBUFFER_SIZE - 1,szMessage,args); m_ListView.AddItem(iItemIndex,SUBITEM_TEXT,m_szStringBuffer); m_ListView.SetColumnWidth(SUBITEM_TEXT,LVSCW_AUTOSIZE); m_ListView.EnsureVisible(iItemIndex,false); } bool CProgressDlg::cancelled() { return m_bCancelled; } void CProgressDlg::SetDevice(const TCHAR *szDevice) { ckcore::tstring DeviceStr = lngGetString(PROGRESS_DEVICE); DeviceStr += szDevice; SetDlgItemText(IDC_DEVICESTATIC,DeviceStr.c_str()); } void CProgressDlg::SetDevice(ckmmc::Device &Device) { ckcore::tstring DeviceStr = lngGetString(PROGRESS_DEVICE); DeviceStr += NDeviceUtil::GetDeviceName(Device); SetDlgItemText(IDC_DEVICESTATIC,DeviceStr.c_str()); } void CProgressDlg::NotifyCompleted() { ::EnableWindow(GetDlgItem(IDOK),true); if ( GetForegroundWindow() == m_hWnd ) { // Change default focus to the OK button. We can only do this // if this window is active. Otherwise, this call will not // make it active, but will still trigger a WM_ACTIVATE message // to this window. // Later on, when this window does get active, it will not // get the corresponding WM_ACTIVATE and we won't be able // to stop the flashing if necessary, see OnActivate() below. SendMessage(WM_NEXTDLGCTL,(WPARAM)::GetDlgItem(m_hWnd,IDOK),0); } else m_bNeedToFocusOkButton = true; ::EnableWindow(GetDlgItem(IDCANCEL),false); if (m_bCancelled) { set_status(lngGetString(PROGRESS_CANCELED)); notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); } // Restore the window title. if (!m_bAppMode && m_szHostTitle != NULL) { GetParentWindow(this).SetWindowText(m_szHostTitle); delete m_szHostTitle; m_szHostTitle = NULL; } SMOKE_STOP // Recording a CD can take some time, and the user may switch to // another application meanwhile and not notice when the CD is finished. // Therefore, at the end of the process, we prompt for // the user's attention by making the window and taskbar icon flash. // // Calling SetForegroundWindow() or SetActiveWindow() // should have an equivalent effect according to the documentation, // but it does not seem to do the trick, we need to call // FlashWindow(). // We don't want to start flashing if this window is the active one // at the moment. We also need to stop the flashing if the window // wasn't active and the user reacts to the flashing and clicks on it. // // Rather than flashing, it would be better to display a balloon notification // on the task bar, but that's only available from Windows XP onwards. if ( m_pFlashWindowEx != NULL && GetForegroundWindow() != m_hWnd ) { FLASHWINFO fi1; ZeroMemory(&fi1, sizeof(fi1)); fi1.cbSize = sizeof(fi1); fi1.hwnd = m_hWnd; fi1.dwFlags = 1; // FLASHW_CAPTION. The taskbar icon belongs to the main window. fi1.uCount = 5; fi1.dwTimeout = 0; m_pFlashWindowEx( &fi1 ); if ( !m_bAppMode ) { FLASHWINFO fi2; ZeroMemory(&fi2, sizeof(fi2)); fi2.cbSize = sizeof(fi2); fi2.hwnd = GetParentWindow(this).m_hWnd; fi2.dwFlags = 2; // FLASHW_TRAY fi2.uCount = 5; fi2.dwTimeout = 0; m_pFlashWindowEx( &fi2 ); } } } LRESULT CProgressDlg::OnActivate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { const UINT nState = LOWORD(wParam); // If this window is getting activated... if (nState != WA_INACTIVE) { // Stop the window flashing. The window may never have flashed, // or may have flashed but may have stopped flashing after the given // flash count, but that doesn't matter. if (m_pFlashWindowEx != NULL) { FLASHWINFO fi1; ZeroMemory(&fi1,sizeof(fi1)); fi1.cbSize = sizeof(fi1); fi1.hwnd = m_hWnd; fi1.dwFlags = 0; // FLASHW_STOP fi1.uCount = 0; fi1.dwTimeout = 0; m_pFlashWindowEx(&fi1); if (!m_bAppMode) { FLASHWINFO fi2; ZeroMemory(&fi2,sizeof(fi2)); fi2.cbSize = sizeof(fi2); fi2.hwnd = GetParentWindow(this).m_hWnd; fi2.dwFlags = 0; // FLASHW_STOP fi2.uCount = 0; fi2.dwTimeout = 0; m_pFlashWindowEx(&fi2); } } if (m_bNeedToFocusOkButton) { SendMessage(WM_NEXTDLGCTL,(WPARAM)::GetDlgItem(m_hWnd,IDOK),0); // Change default focus to the OK button. m_bNeedToFocusOkButton = false; } } return 0; } void CProgressDlg::SetBuffer(int iPercent) { SendDlgItemMessage(IDC_BUFFERPROGRESS,PBM_SETPOS,(WPARAM)iPercent,0); } void CProgressDlg::AllowReload() { ::ShowWindow(GetDlgItem(IDC_RELOADBUTTON),SW_SHOW); } void CProgressDlg::AllowCancel(bool bAllow) { ::EnableWindow(GetDlgItem(IDCANCEL),bAllow); } void CProgressDlg::Reset() { m_bRealMode = false; m_bCancelled = false; } bool CProgressDlg::RequestNextDisc() { return lngMessageBox(m_hWnd,INFO_NEXTCOPY,GENERAL_INFORMATION,MB_OKCANCEL | MB_ICONINFORMATION) == IDOK; } void CProgressDlg::StartSmoke() { SMOKE_START } LRESULT CProgressDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { DlgResize_Init(); CenterWindow(GetParent()); // If we're in application mode, add a minimize button to the window. // UPDATE: This does not work, nor is it a good idea regarding the smoke effect. /*if (m_bAppMode) ModifyStyle(0,WS_MINIMIZEBOX,0);*/ SendDlgItemMessage(IDC_TOTALPROGRESS,PBM_SETRANGE32,0,100); SendDlgItemMessage(IDC_BUFFERPROGRESS,PBM_SETRANGE32,0,100); // Make the static controls double buffered. m_TotalStatic.SubclassWindow(GetDlgItem(IDC_TOTALSTATIC)); m_StatusStatic.SubclassWindow(GetDlgItem(IDC_STATUSSTATIC)); // Initialize the list view. m_ListView = GetDlgItem(IDC_MESSAGELIST); m_ListView.SetImageList(m_hListImageList,LVSIL_NORMAL); m_ListView.SetImageList(m_hListImageList,LVSIL_SMALL); m_ListView.SetExtendedListViewStyle(LVS_EX_FULLROWSELECT); m_ListView.AddColumn(lngGetString(COLUMN_TIME),0); m_ListView.SetColumnWidth(0,70); m_ListView.AddColumn(lngGetString(COLUMN_EVENT),1); m_ListView.SetColumnWidth(1,150); // Disable the OK button. ::EnableWindow(GetDlgItem(IDOK),false); set_progress(0); // Translate the window. Translate(); if (!m_bAppMode) { if (m_szHostTitle != NULL) delete [] m_szHostTitle; int iSize = GetParentWindow(this).GetWindowTextLength() + 1; m_szHostTitle = new TCHAR[iSize]; GetParentWindow(this).GetWindowText(m_szHostTitle,iSize); } return TRUE; } LRESULT CProgressDlg::OnReload(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Send a CR-LF message to inform CD-tools that the drive has been reloaded. if (m_pProcess != NULL) m_pProcess->write("\r\n",2); // Hide the reload button. ::ShowWindow(GetDlgItem(IDC_RELOADBUTTON),SW_HIDE); return FALSE; } LRESULT CProgressDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Re-enable the main window. if (::IsWindow(m_hWndHost)) ::EnableWindow(m_hWndHost,true); DestroyWindow(); // If we're in application mode we post a quit message. if (m_bAppMode) ::PostQuitMessage(wID); return FALSE; } LRESULT CProgressDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Make sure that we're allowed to cancel. if (!::IsWindowEnabled(GetDlgItem(IDCANCEL))) return TRUE; // If we're in real mode we dispay a warning message informing the user that // aborting might permanently damage the CD. if (m_bRealMode) { if (lngMessageBox(m_hWnd,CONFIRM_WRITECANCEL,GENERAL_WARNING,MB_YESNO | MB_ICONWARNING) == IDNO) return TRUE; } m_bCancelled = true; if (m_pProcess != NULL) m_pProcess->kill(); // Hide the reload button. ::ShowWindow(GetDlgItem(IDC_RELOADBUTTON),SW_HIDE); return TRUE; } LRESULT CProgressDlg::OnListViewDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { ATLASSERT(iCtrlID == IDC_MESSAGELIST); LPNMITEMACTIVATE pItemActivate = (LPNMITEMACTIVATE)pNMH; _bstr_t LineText; m_ListView.GetItemText(pItemActivate->iItem,SUBITEM_TEXT,LineText.GetBSTR()); MessageBox(LineText,_T("Log line"),MB_OK | MB_ICONINFORMATION); bHandled = TRUE; return 0; } ================================================ FILE: src/app/dialog/progress_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include "resource.h" #include "advanced_progress.hh" #include "double_buffered_static.hh" #include "effects.hh" #include "version.hh" #ifndef PBM_SETMARQUEE #define PBM_SETMARQUEE (WM_USER + 10) #endif #ifndef PBS_MARQUEE #define PBS_MARQUEE 0x08 #endif class CProgressDlg : public CDialogImpl, public CDialogResize, public CAdvancedProgress { private: #if(WINVER < 0x0500) typedef struct { UINT cbSize; HWND hwnd; DWORD dwFlags; UINT uCount; DWORD dwTimeout; } FLASHWINFO, *PFLASHWINFO; #endif // #if(WINVER < 0x0500) typedef BOOL (WINAPI *PointerToFlashWindowEx)(PFLASHWINFO); PointerToFlashWindowEx m_pFlashWindowEx; bool m_bNeedToFocusOkButton; HIMAGELIST m_hListImageList; CListViewCtrl m_ListView; CDoubleBufferedStatic m_TotalStatic; CDoubleBufferedStatic m_StatusStatic; ckcore::Process *m_pProcess; bool m_bAppMode; bool m_bRealMode; bool m_bCancelled; HWND m_hWndHost; unsigned char m_ucPercent; TCHAR *m_szHostTitle; bool Translate(); public: enum { IDD = IDD_PROGRESSDLG }; CProgressDlg(); ~CProgressDlg(); void AttachProcess(ckcore::Process *pProcess); void AttachHost(HWND hWndHost); void SetAppMode(bool bAppMode); void SetRealMode(bool bRealMode); // ckcore::Progress. void set_progress(unsigned char ucPercent); void set_marquee(bool bMarquee); void set_status(const TCHAR *szStatus,...); void notify(ckcore::Progress::MessageType Type,const TCHAR *szMessage,...); bool cancelled(); void SetDevice(const TCHAR *szDevice); void SetDevice(ckmmc::Device &Device); void NotifyCompleted(); void SetBuffer(int iPercent); void AllowReload(); void AllowCancel(bool bAllow); void Reset(); bool RequestNextDisc(); void StartSmoke(); private: BEGIN_MSG_MAP(CProgressDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_ACTIVATE,OnActivate) COMMAND_ID_HANDLER(IDC_RELOADBUTTON,OnReload) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) NOTIFY_HANDLER(IDC_MESSAGELIST,NM_DBLCLK,OnListViewDblClick) SMOKE_EVENTS CHAIN_MSG_MAP(CDialogResize) END_MSG_MAP() // Resize maps. BEGIN_DLGRESIZE_MAP(CProgressDlg) DLGRESIZE_CONTROL(IDC_TOTALSTATIC,DLSZ_SIZE_X) DLGRESIZE_CONTROL(IDC_TOTALPROGRESS,DLSZ_SIZE_X) DLGRESIZE_CONTROL(IDC_STATUSSTATIC,DLSZ_SIZE_X) DLGRESIZE_CONTROL(IDC_MESSAGELIST,DLSZ_SIZE_X | DLSZ_SIZE_Y) DLGRESIZE_CONTROL(IDC_BEVELSTATIC,DLSZ_SIZE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_DEVICESTATIC,DLSZ_SIZE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_BUFFERSTATIC,DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_BUFFERPROGRESS,DLSZ_SIZE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDOK,DLSZ_MOVE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDCANCEL,DLSZ_MOVE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_RELOADBUTTON,DLSZ_MOVE_X | DLSZ_MOVE_Y) END_DLGRESIZE_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnActivate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnReload(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnListViewDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); SMOKE_IMPL }; extern CProgressDlg * g_pProgressDlg; ================================================ FILE: src/app/dialog/project_prop_audio_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_prop_audio_page.hh" #include "settings.hh" #include "string_table.hh" #include "project_manager.hh" #include "edit_track_dlg.hh" #include "lang_util.hh" #include "trans_util.hh" CProjectPropAudioPage::CProjectPropAudioPage() { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_AUDIO,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CProjectPropAudioPage::~CProjectPropAudioPage() { } bool CProjectPropAudioPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a projectprop translation section. if (!pLng->EnterSection(_T("projectprop"))) return false; // Translate. TCHAR *szStrValue; int iMaxStaticRight = 0; if (pLng->GetValuePtr(IDC_ALBUMSTATIC,szStrValue)) { SetDlgItemText(IDC_ALBUMSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_ALBUMSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_ARTISTSTATIC,szStrValue)) { SetDlgItemText(IDC_ARTISTSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_ARTISTSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_INFOSTATIC,szStrValue)) SetDlgItemText(IDC_INFOSTATIC,szStrValue); // Make sure that the edit/combo controls are not in the way of the statics. if (iMaxStaticRight > 75) { UpdateEditPos(m_hWnd,IDC_ALBUMEDIT,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_ARTISTEDIT,iMaxStaticRight); } return true; } bool CProjectPropAudioPage::OnApply() { GetDlgItemText(IDC_ALBUMEDIT,g_ProjectSettings.m_szAlbumName,159); GetDlgItemText(IDC_ARTISTEDIT,g_ProjectSettings.m_szAlbumArtist,159); return true; } void CProjectPropAudioPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/working_with_projects/project_settings.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CProjectPropAudioPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Setup the list view. m_ListView = GetDlgItem(IDC_TRACKLIST); m_ListView.SetExtendedListViewStyle(LVS_EX_FULLROWSELECT); m_ListView.InsertColumn(0,lngGetString(COLUMN_TRACK),LVCFMT_LEFT,45,0); m_ListView.InsertColumn(1,lngGetString(COLUMN_TITLE),LVCFMT_LEFT,150,1); m_ListView.InsertColumn(2,lngGetString(COLUMN_ARTIST),LVCFMT_LEFT,118,2); g_ProjectManager.ListAudioTracks(&m_ListView); // Load the album information. SetDlgItemText(IDC_ALBUMEDIT,g_ProjectSettings.m_szAlbumName); SetDlgItemText(IDC_ARTISTEDIT,g_ProjectSettings.m_szAlbumArtist); // Translate the window. Translate(); return TRUE; } LRESULT CProjectPropAudioPage::OnListDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { if (m_ListView.GetSelectedCount() > 0) { unsigned int uiTrackIndex = m_ListView.GetSelectedIndex(); CItemData *pItemData = (CItemData *)m_ListView.GetItemData(uiTrackIndex); TCHAR szTitle[64]; lsnprintf_s(szTitle,64,lngGetString(PROJECTPROP_TRACKPROP),uiTrackIndex + 1); CEditTrackDlg EditTrackDlg(pItemData); if (EditTrackDlg.DoModal(::GetActiveWindow(),(LPARAM)szTitle) == IDOK) { m_ListView.SetItemText(uiTrackIndex,1,pItemData->GetAudioData()->szTrackTitle); m_ListView.SetItemText(uiTrackIndex,2,pItemData->GetAudioData()->szTrackArtist); } } bHandled = false; return 0; } ================================================ FILE: src/app/dialog/project_prop_audio_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CProjectPropAudioPage : public CPropertyPageImpl { private: CListViewCtrl m_ListView; bool Translate(); public: enum { IDD = IDD_PROPPAGE_PROJECTPROPAUDIO }; CProjectPropAudioPage(); ~CProjectPropAudioPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CProjectPropAudioPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) NOTIFY_HANDLER(IDC_TRACKLIST,NM_DBLCLK,OnListDblClick) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnListDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/project_prop_boot_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_prop_boot_page.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "version.hh" #include "add_boot_image_dlg.hh" #include "project_manager.hh" #include "trans_util.hh" CProjectPropBootPage::CProjectPropBootPage() { m_hToolBarImageList = NULL; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_BOOT,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CProjectPropBootPage::~CProjectPropBootPage() { if (m_hToolBarImageList) ImageList_Destroy(m_hToolBarImageList); } bool CProjectPropBootPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a projectprop translation section. if (!pLng->EnterSection(_T("projectprop"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_BOOTSTATIC,szStrValue)) SetDlgItemText(IDC_BOOTSTATIC,szStrValue); return true; } void CProjectPropBootPage::InitToolBarImageList() { // Create the image list. HBITMAP hBitmap; if (g_WinVer.m_ulMajorCCVersion >= 6) { hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MINITOOLBARBITMAP)); m_hToolBarImageList = ImageList_Create(16,16,ILC_COLOR32,0,6); ImageList_Add(m_hToolBarImageList,hBitmap,NULL); } else { hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_MINITOOLBARBITMAP_)); m_hToolBarImageList = ImageList_Create(16,16,ILC_COLOR32 | ILC_MASK,0,6); ImageList_AddMasked(m_hToolBarImageList,hBitmap,RGB(255,0,255)); } DeleteObject(hBitmap); } void CProjectPropBootPage::AddToolBarButton(int iCommand,int iBitmap) { TBBUTTON tbButton; tbButton.fsState = TBSTATE_ENABLED; tbButton.fsStyle = TBSTYLE_BUTTON; tbButton.iBitmap = iBitmap; tbButton.idCommand = iCommand; tbButton.iString = 0; tbButton.dwData = 0; m_ToolBar.InsertButton(m_ToolBar.GetButtonCount(),&tbButton); } void CProjectPropBootPage::CreateToolBarCtrl() { RECT rcListView; ::GetWindowRect(GetDlgItem(IDC_LIST),&rcListView); ScreenToClient(&rcListView); RECT rcToolBar = { 0,0,100,100 }; m_ToolBar.Create(m_hWnd,rcToolBar,NULL,ATL_SIMPLE_TOOLBAR_PANE_STYLE,NULL); m_ToolBar.SetImageList(m_hToolBarImageList); m_ToolBar.SetButtonStructSize(); // Create the buttons. AddToolBarButton(ID_BOOT_ADD,1); AddToolBarButton(ID_BOOT_REMOVE,3); AddToolBarButton(ID_BOOT_EDIT,6); m_ToolBar.EnableButton(ID_BOOT_REMOVE,false); m_ToolBar.EnableButton(ID_BOOT_EDIT,false); // Update the toolbar position. int iToolBarWidth = 0; RECT rcButton; for (int i = 0; i < m_ToolBar.GetButtonCount(); i++) { m_ToolBar.GetItemRect(i,&rcButton); iToolBarWidth += rcButton.right - rcButton.left; } m_ToolBar.SetWindowPos(NULL, rcListView.right - iToolBarWidth, rcListView.top - HIWORD(m_ToolBar.GetButtonSize()), iToolBarWidth, HIWORD(m_ToolBar.GetButtonSize()),0); } void CProjectPropBootPage::FillListView() { int iItemCount = 0; std::list ::iterator itImageObject; for (itImageObject = g_ProjectSettings.m_BootImages.begin(); itImageObject != g_ProjectSettings.m_BootImages.end(); itImageObject++) { m_ListView.AddItem(iItemCount,0,LPSTR_TEXTCALLBACK); m_ListView.AddItem(iItemCount,1,LPSTR_TEXTCALLBACK); m_ListView.SetItemData(iItemCount++,(DWORD_PTR)*itImageObject); } } bool CProjectPropBootPage::OnApply() { return true; } void CProjectPropBootPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/working_with_projects/project_settings.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CProjectPropBootPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Create the toolbar. InitToolBarImageList(); CreateToolBarCtrl(); // Initialize the list view. m_ListView = GetDlgItem(IDC_LIST); m_ListView.AddColumn(lngGetString(COLUMN_NAME),0); m_ListView.AddColumn(lngGetString(COLUMN_EMULATION),1); m_ListView.SetColumnWidth(0,253); m_ListView.SetExtendedListViewStyle(LVS_EX_FULLROWSELECT); // Translate the window. Translate(); // Fill the list view. FillListView(); return TRUE; } LRESULT CProjectPropBootPage::OnListAdd(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { bHandled = false; // The maximum number of allowed boot images is 63. if (m_ListView.GetItemCount() == 63) { MessageBox(lngGetString(ERROR_NUMBOOTIMAGES),lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return 0; } WTL::CFileDialog FileDialog(true,0,0,OFN_FILEMUSTEXIST | OFN_EXPLORER, _T("All Files (*.*)\0*.*\0\0"),m_hWnd); if (FileDialog.DoModal() == IDOK) { CProjectBootImage *pBootImage = new CProjectBootImage(); pBootImage->m_FullPath = FileDialog.m_szFileName; ExtractFileName(FileDialog.m_szFileName); pBootImage->m_LocalName = FileDialog.m_szFileName; CAddBootImageDlg AddBootImageDlg(pBootImage,false); if (AddBootImageDlg.DoModal() == IDOK) { g_ProjectSettings.m_BootImages.push_back(pBootImage); int iItemCount = m_ListView.GetItemCount(); m_ListView.AddItem(iItemCount,0,LPSTR_TEXTCALLBACK); m_ListView.AddItem(iItemCount,1,LPSTR_TEXTCALLBACK); m_ListView.SetItemData(iItemCount,(DWORD_PTR)pBootImage); return 0; } delete pBootImage; } return 0; } LRESULT CProjectPropBootPage::OnListRemove(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { bHandled = false; CProjectBootImage *pBootImage = reinterpret_cast(m_ListView.GetItemData(m_ListView.GetSelectedIndex())); g_ProjectSettings.m_BootImages.remove(pBootImage); // Deltete the item from the list view. m_ListView.DeleteItem(m_ListView.GetSelectedIndex()); return 0; } LRESULT CProjectPropBootPage::OnListEdit(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { int iSelected = m_ListView.GetSelectedIndex(); CProjectBootImage *pBootImage = (CProjectBootImage *)m_ListView.GetItemData(iSelected); CAddBootImageDlg AddBootImageDlg(pBootImage,true); if (AddBootImageDlg.DoModal() == IDOK) { m_ListView.Update(iSelected); } bHandled = false; return 0; } LRESULT CProjectPropBootPage::OnToolBarGetInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { bHandled = true; // The string ID is the same as the button ID. LPTOOLTIPTEXT pTipText = (LPTOOLTIPTEXT)pNMH; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a hint translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("hint"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr((unsigned long)pTipText->hdr.idFrom,szStrValue)) { pTipText->lpszText = szStrValue; return 0; } } } pTipText->lpszText = MAKEINTRESOURCE(pTipText->hdr.idFrom); return 0; } LRESULT CProjectPropBootPage::OnListItemChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { if (m_ToolBar.IsWindow()) { if (m_ListView.GetSelectedCount() > 0) { m_ToolBar.EnableButton(ID_BOOT_REMOVE,true); m_ToolBar.EnableButton(ID_BOOT_EDIT,true); } else { m_ToolBar.EnableButton(ID_BOOT_REMOVE,false); m_ToolBar.EnableButton(ID_BOOT_EDIT,false); } } bHandled = false; return 0; } LRESULT CProjectPropBootPage::OnListGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { NMLVDISPINFO *pDispInfo = (NMLVDISPINFO *)pNMH; CProjectBootImage *pBootImage = (CProjectBootImage *)pDispInfo->item.lParam; if (pDispInfo->item.mask & LVIF_TEXT) { switch (pDispInfo->item.iSubItem) { case 0: lstrcpy(pDispInfo->item.pszText,pBootImage->m_FullPath.c_str()); break; case 1: { switch (pBootImage->m_iEmulation) { case PROJECTBI_BOOTEMU_FLOPPY: lstrcpy(pDispInfo->item.pszText,lngGetString(BOOTEMU_FLOPPY)); break; case PROJECTBI_BOOTEMU_HARDDISK: lstrcpy(pDispInfo->item.pszText,lngGetString(BOOTEMU_HARDDISK)); break; default: lstrcpy(pDispInfo->item.pszText,lngGetString(BOOTEMU_NONE)); break; } } break; } } bHandled = false; return 0; } ================================================ FILE: src/app/dialog/project_prop_boot_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CProjectPropBootPage : public CPropertyPageImpl { private: HIMAGELIST m_hToolBarImageList; CListViewCtrl m_ListView; CToolBarCtrl m_ToolBar; bool Translate(); void InitToolBarImageList(); void AddToolBarButton(int iCommand,int iBitmap); void CreateToolBarCtrl(); void FillListView(); public: enum { IDD = IDD_PROPPAGE_PROJECTPROPBOOT }; CProjectPropBootPage(); ~CProjectPropBootPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CProjectPropBootPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(ID_BOOT_ADD,OnListAdd) COMMAND_ID_HANDLER(ID_BOOT_REMOVE,OnListRemove) COMMAND_ID_HANDLER(ID_BOOT_EDIT,OnListEdit) NOTIFY_CODE_HANDLER(TTN_GETDISPINFO,OnToolBarGetInfo) NOTIFY_HANDLER(IDC_LIST,LVN_ITEMCHANGED,OnListItemChanged) NOTIFY_HANDLER(IDC_LIST,LVN_GETDISPINFO,OnListGetDispInfo) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnListAdd(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnListRemove(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnListEdit(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnToolBarGetInfo(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnListItemChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnListGetDispInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/project_prop_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_prop_dlg.hh" #include "project_manager.hh" #include "string_table.hh" #include "lang_util.hh" #include "settings.hh" CProjectPropDlg::CProjectPropDlg() : CPropertySheetImpl(lngGetString(PROJECTPROP_TITLE),0,NULL) { m_bCentered = false; m_psh.dwFlags |= PSH_NOAPPLYNOW | PSH_HASHELP | PSH_NOCONTEXTHELP; m_hGeneralPage = ::CreatePropertySheetPage(m_GeneralPage); m_hFileSysPage = ::CreatePropertySheetPage(m_FileSysPage); m_hIsoPage = ::CreatePropertySheetPage(m_IsoPage); m_hFieldsPage = ::CreatePropertySheetPage(m_FieldsPage); m_hBootPage = ::CreatePropertySheetPage(m_BootPage); m_hUdfPage = ::CreatePropertySheetPage(m_UdfPage); m_hAudioPage = ::CreatePropertySheetPage(m_AudioPage); AddPage(m_hGeneralPage); switch (g_ProjectManager.GetProjectType()) { case PROJECTTYPE_DATA: AddPage(m_hFileSysPage); if (g_ProjectSettings.m_iFileSystem == FILESYSTEM_ISO_UDF || g_ProjectSettings.m_iFileSystem == FILESYSTEM_UDF || g_ProjectSettings.m_iFileSystem == FILESYSTEM_DVDVIDEO) { AddPage(m_hUdfPage); } if (g_ProjectSettings.m_iFileSystem == FILESYSTEM_ISO || g_ProjectSettings.m_iFileSystem == FILESYSTEM_ISO_UDF || g_ProjectSettings.m_iFileSystem == FILESYSTEM_DVDVIDEO) { AddPage(m_hIsoPage); AddPage(m_hFieldsPage); AddPage(m_hBootPage); } break; case PROJECTTYPE_AUDIO: AddPage(m_hAudioPage); break; case PROJECTTYPE_MIXED: AddPage(m_hAudioPage); AddPage(m_hFileSysPage); if (g_ProjectSettings.m_iFileSystem == FILESYSTEM_ISO_UDF || g_ProjectSettings.m_iFileSystem == FILESYSTEM_UDF || g_ProjectSettings.m_iFileSystem == FILESYSTEM_DVDVIDEO) { AddPage(m_hUdfPage); } if (g_ProjectSettings.m_iFileSystem == FILESYSTEM_ISO || g_ProjectSettings.m_iFileSystem == FILESYSTEM_ISO_UDF || g_ProjectSettings.m_iFileSystem == FILESYSTEM_DVDVIDEO) { AddPage(m_hIsoPage); AddPage(m_hFieldsPage); AddPage(m_hBootPage); } break; }; } CProjectPropDlg::~CProjectPropDlg() { } LRESULT CProjectPropDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } bHandled = false; return 0; } LRESULT CProjectPropDlg::OnSetFileSystem(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { switch (lParam) { case FILESYSTEM_ISO: if (wParam == FILESYSTEM_UDF) // Check previous selection. { m_hIsoPage = ::CreatePropertySheetPage(m_IsoPage); m_hFieldsPage = ::CreatePropertySheetPage(m_FieldsPage); m_hBootPage = ::CreatePropertySheetPage(m_BootPage); AddPage(m_hIsoPage); AddPage(m_hFieldsPage); AddPage(m_hBootPage); } if (wParam != FILESYSTEM_ISO) { RemovePage(m_hUdfPage); } break; case FILESYSTEM_UDF: if (wParam != FILESYSTEM_UDF) // Check previous selection. { RemovePage(m_hIsoPage); RemovePage(m_hFieldsPage); RemovePage(m_hBootPage); } if (wParam == FILESYSTEM_ISO) { m_hUdfPage = ::CreatePropertySheetPage(m_UdfPage); AddPage(m_hUdfPage); } break; case FILESYSTEM_ISO_UDF: case FILESYSTEM_DVDVIDEO: if (wParam == FILESYSTEM_UDF) // Check previous selection. { m_hIsoPage = ::CreatePropertySheetPage(m_IsoPage); m_hFieldsPage = ::CreatePropertySheetPage(m_FieldsPage); m_hBootPage = ::CreatePropertySheetPage(m_BootPage); AddPage(m_hIsoPage); AddPage(m_hFieldsPage); AddPage(m_hBootPage); } else if (wParam == FILESYSTEM_ISO) { m_hUdfPage = ::CreatePropertySheetPage(m_UdfPage); InsertPage(2,m_hUdfPage); } break; } bHandled = true; return 0; } ================================================ FILE: src/app/dialog/project_prop_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "project_prop_general_page.hh" #include "project_prop_file_sys_page.hh" #include "project_prop_iso_page.hh" #include "project_prop_fields_page.hh" #include "project_prop_audio_page.hh" #include "project_prop_boot_page.hh" #include "project_prop_udf_page.hh" #include "ctrl_messages.hh" class CProjectPropDlg : public CPropertySheetImpl { private: bool m_bCentered; CProjectPropGeneralPage m_GeneralPage; CProjectPropFileSysPage m_FileSysPage; CProjectPropIsoPage m_IsoPage; CProjectPropFieldsPage m_FieldsPage; CProjectPropBootPage m_BootPage; CProjectPropUdfPage m_UdfPage; CProjectPropAudioPage m_AudioPage; HPROPSHEETPAGE m_hGeneralPage; HPROPSHEETPAGE m_hFileSysPage; HPROPSHEETPAGE m_hIsoPage; HPROPSHEETPAGE m_hFieldsPage; HPROPSHEETPAGE m_hBootPage; HPROPSHEETPAGE m_hUdfPage; HPROPSHEETPAGE m_hAudioPage; public: CProjectPropDlg(); ~CProjectPropDlg(); BEGIN_MSG_MAP(CProjectPropDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) MESSAGE_HANDLER(WM_SETFILESYSTEM,OnSetFileSystem); CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnSetFileSystem(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/project_prop_fields_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_prop_fields_page.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "trans_util.hh" CProjectPropFieldsPage::CProjectPropFieldsPage() { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_FIELDS,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CProjectPropFieldsPage::~CProjectPropFieldsPage() { } bool CProjectPropFieldsPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a projectprop translation section. if (!pLng->EnterSection(_T("projectprop"))) return false; // Translate. TCHAR *szStrValue; int iMaxStaticRight = 0; if (pLng->GetValuePtr(IDC_PUBLISHERSTATIC,szStrValue)) { SetDlgItemText(IDC_PUBLISHERSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_PUBLISHERSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_PREPARERSTATIC,szStrValue)) { SetDlgItemText(IDC_PREPARERSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_PREPARERSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_SYSTEMSTATIC,szStrValue)) { SetDlgItemText(IDC_SYSTEMSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_SYSTEMSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_VOLUMESTATIC,szStrValue)) { SetDlgItemText(IDC_VOLUMESTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_VOLUMESTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_COPYRIGHTSTATIC,szStrValue)) { SetDlgItemText(IDC_COPYRIGHTSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_COPYRIGHTSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_ABSTRACTSTATIC,szStrValue)) { SetDlgItemText(IDC_ABSTRACTSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_ABSTRACTSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_BIBLIOGRAPHICSTATIC,szStrValue)) { SetDlgItemText(IDC_BIBLIOGRAPHICSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_BIBLIOGRAPHICSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } // Make sure that the edit controls are not in the way of the statics. if (iMaxStaticRight > 75) { UpdateEditPos(m_hWnd,IDC_PUBLISHEREDIT,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_PREPAREREDIT,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_SYSTEMEDIT,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_VOLUMEEDIT,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_COPYRIGHTEDIT,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_ABSTRACTEDIT,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_BIBLIOGRAPHICEDIT,iMaxStaticRight); } return true; } bool CProjectPropFieldsPage::OnApply() { GetDlgItemText(IDC_PUBLISHEREDIT,g_ProjectSettings.m_szPublisher,127); GetDlgItemText(IDC_PREPAREREDIT,g_ProjectSettings.m_szPreparer,127); GetDlgItemText(IDC_SYSTEMEDIT,g_ProjectSettings.m_szSystem,127); GetDlgItemText(IDC_VOLUMEEDIT,g_ProjectSettings.m_szVolumeSet,127); GetDlgItemText(IDC_COPYRIGHTEDIT,g_ProjectSettings.m_szCopyright,36); GetDlgItemText(IDC_ABSTRACTEDIT,g_ProjectSettings.m_szAbstract,36); GetDlgItemText(IDC_BIBLIOGRAPHICEDIT,g_ProjectSettings.m_szBibliographic,36); return true; } void CProjectPropFieldsPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/working_with_projects/project_settings.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CProjectPropFieldsPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Set field length limits. ::SendMessage(GetDlgItem(IDC_PUBLISHEREDIT),EM_SETLIMITTEXT,127,0); ::SendMessage(GetDlgItem(IDC_PREPAREREDIT),EM_SETLIMITTEXT,127,0); ::SendMessage(GetDlgItem(IDC_SYSTEMEDIT),EM_SETLIMITTEXT,127,0); ::SendMessage(GetDlgItem(IDC_VOLUMEEDIT),EM_SETLIMITTEXT,127,0); ::SendMessage(GetDlgItem(IDC_COPYRIGHTEDIT),EM_SETLIMITTEXT,36,0); ::SendMessage(GetDlgItem(IDC_ABSTRACTEDIT),EM_SETLIMITTEXT,36,0); ::SendMessage(GetDlgItem(IDC_BIBLIOGRAPHICEDIT),EM_SETLIMITTEXT,36,0); // Load the default settings. SetDlgItemText(IDC_PUBLISHEREDIT,g_ProjectSettings.m_szPublisher); SetDlgItemText(IDC_PREPAREREDIT,g_ProjectSettings.m_szPreparer); SetDlgItemText(IDC_SYSTEMEDIT,g_ProjectSettings.m_szSystem); SetDlgItemText(IDC_VOLUMEEDIT,g_ProjectSettings.m_szVolumeSet); SetDlgItemText(IDC_COPYRIGHTEDIT,g_ProjectSettings.m_szCopyright); SetDlgItemText(IDC_ABSTRACTEDIT,g_ProjectSettings.m_szAbstract); SetDlgItemText(IDC_BIBLIOGRAPHICEDIT,g_ProjectSettings.m_szBibliographic); // Translate the window. Translate(); return true; } ================================================ FILE: src/app/dialog/project_prop_fields_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CProjectPropFieldsPage : public CPropertyPageImpl { private: bool Translate(); public: enum { IDD = IDD_PROPPAGE_PROJECTPROPFIELDS }; CProjectPropFieldsPage(); ~CProjectPropFieldsPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CProjectPropFieldsPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/project_prop_file_sys_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_prop_file_sys_page.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "trans_util.hh" #include "ctrl_messages.hh" CProjectPropFileSysPage::CProjectPropFileSysPage() { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_FILESYSTEM,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CProjectPropFileSysPage::~CProjectPropFileSysPage() { } bool CProjectPropFileSysPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a projectprop translation section. if (!pLng->EnterSection(_T("projectprop"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_FILESYSSTATIC,szStrValue)) SetDlgItemText(IDC_FILESYSSTATIC,szStrValue); return true; } bool CProjectPropFileSysPage::OnApply() { g_ProjectSettings.m_iFileSystem = (int)m_FileSysCombo.GetItemData(m_FileSysCombo.GetCurSel()); return true; } void CProjectPropFileSysPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/working_with_projects/project_settings.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CProjectPropFileSysPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Setup the file system combo box. m_FileSysCombo = GetDlgItem(IDC_FILESYSCOMBO); int iIndex = 0; m_FileSysCombo.AddString(_T("ISO9660")); m_FileSysCombo.SetItemData(iIndex++,FILESYSTEM_ISO); m_FileSysCombo.AddString(_T("ISO9660 + UDF")); m_FileSysCombo.SetItemData(iIndex++,FILESYSTEM_ISO_UDF); m_FileSysCombo.AddString(_T("ISO9660 + UDF (DVD-Video)")); m_FileSysCombo.SetItemData(iIndex++,FILESYSTEM_DVDVIDEO); m_FileSysCombo.AddString(_T("UDF")); m_FileSysCombo.SetItemData(iIndex++,FILESYSTEM_UDF); bool bFoundItem = false; for (int i = 0; i < m_FileSysCombo.GetCount(); i++) { if (static_cast(m_FileSysCombo.GetItemData(i)) == g_ProjectSettings.m_iFileSystem) { m_FileSysCombo.SetCurSel(i); bFoundItem = true; break; } } if (!bFoundItem) m_FileSysCombo.SetCurSel(0); m_iSelFileSystem = g_ProjectSettings.m_iFileSystem; if (g_ProjectSettings.m_bMultiSession) m_FileSysCombo.EnableWindow(FALSE); // Translate the window. Translate(); return true; } LRESULT CProjectPropFileSysPage::OnFileSysChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { ::SendMessage(GetParent(),WM_SETFILESYSTEM,m_iSelFileSystem,m_FileSysCombo.GetItemData(m_FileSysCombo.GetCurSel())); m_iSelFileSystem = (int)m_FileSysCombo.GetItemData(m_FileSysCombo.GetCurSel()); bHandled = false; return 0; } ================================================ FILE: src/app/dialog/project_prop_file_sys_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CProjectPropFileSysPage : public CPropertyPageImpl { private: int m_iSelFileSystem; // To keep track of the previously selected file system. CComboBox m_FileSysCombo; bool Translate(); public: enum { IDD = IDD_PROPPAGE_PROJECTPROPFILESYS }; CProjectPropFileSysPage(); ~CProjectPropFileSysPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CProjectPropFileSysPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_HANDLER(IDC_FILESYSCOMBO,CBN_SELCHANGE,OnFileSysChange) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnFileSysChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/project_prop_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "project_prop_general_page.hh" #include "project_manager.hh" #include "string_table.hh" #include "settings.hh" #include "lang_util.hh" CProjectPropGeneralPage::CProjectPropGeneralPage() { m_hIcon = NULL; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_GENERAL,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CProjectPropGeneralPage::~CProjectPropGeneralPage() { if (m_hIcon != NULL) DestroyIcon(m_hIcon); } bool CProjectPropGeneralPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a projectprop translation section. if (!pLng->EnterSection(_T("projectprop"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_TYPELABELSTATIC,szStrValue)) SetDlgItemText(IDC_TYPELABELSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_SIZELABELSTATIC,szStrValue)) SetDlgItemText(IDC_SIZELABELSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_CONTAINSLABELSTATIC,szStrValue)) SetDlgItemText(IDC_CONTAINSLABELSTATIC,szStrValue); return true; } bool CProjectPropGeneralPage::OnApply() { GetDlgItemText(IDC_NAMEEDIT,g_ProjectSettings.m_szLabel,127); return true; } void CProjectPropGeneralPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/working_with_projects/project_settings.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } void CProjectPropGeneralPage::SetupDataProject() { TCHAR szBuffer[64]; // Create the icon. m_hIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_DATAICON), IMAGE_ICON,GetSystemMetrics(SM_CXICON),GetSystemMetrics(SM_CYICON),LR_DEFAULTCOLOR); SendMessage(GetDlgItem(IDC_ICONSTATIC),STM_SETICON,(WPARAM)m_hIcon,0L); // Label name. SetDlgItemText(IDC_NAMEEDIT,g_ProjectSettings.m_szLabel); // Type. SetDlgItemText(IDC_TYPESTATIC,lngGetString(PROJECT_DATA)); // Size. unsigned __int64 uiSize = g_ProjectManager.GetProjectSize(); TCHAR szSizeText[32]; FormatBytes(szBuffer,uiSize); lsprintf(szSizeText,_T(" (%I64d Bytes)"),uiSize); lstrcat(szBuffer,szSizeText); SetDlgItemText(IDC_SIZESTATIC,szBuffer); // Contents. unsigned __int64 uiFileCount,uiFolderCount,uiTrackCount; g_ProjectManager.GetProjectContents(uiFileCount,uiFolderCount,uiTrackCount); lsnprintf_s(szBuffer,64,lngGetString(PROJECT_CONTENTS),uiFileCount,uiFolderCount,uiTrackCount); SetDlgItemText(IDC_CONTAINSSTATIC,szBuffer); } void CProjectPropGeneralPage::SetupAudioProject() { TCHAR szBuffer[64]; // Create the icon. m_hIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_AUDIOICON), IMAGE_ICON,GetSystemMetrics(SM_CXICON),GetSystemMetrics(SM_CYICON),LR_DEFAULTCOLOR); SendMessage(GetDlgItem(IDC_ICONSTATIC),STM_SETICON,(WPARAM)m_hIcon,0L); // Label name. SetDlgItemText(IDC_NAMEEDIT,lngGetString(MISC_NOTAVAILABLE)); ::EnableWindow(GetDlgItem(IDC_NAMEEDIT),false); // Type. SetDlgItemText(IDC_TYPESTATIC,lngGetString(PROJECT_AUDIO)); // Size. lsnprintf_s(szBuffer,64,lngGetString(MISC_MINUTES),g_ProjectManager.GetProjectSize()/(1000 * 60)); SetDlgItemText(IDC_SIZESTATIC,szBuffer); // Contents. unsigned __int64 uiFileCount,uiFolderCount,uiTrackCount; g_ProjectManager.GetProjectContents(uiFileCount,uiFolderCount,uiTrackCount); lsnprintf_s(szBuffer,64,lngGetString(PROJECT_CONTENTS),uiFileCount,uiFolderCount,uiTrackCount); SetDlgItemText(IDC_CONTAINSSTATIC,szBuffer); } void CProjectPropGeneralPage::SetupMixedProject() { TCHAR szBuffer[64]; // Create the icon. m_hIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_MIXEDICON), IMAGE_ICON,GetSystemMetrics(SM_CXICON),GetSystemMetrics(SM_CYICON),LR_DEFAULTCOLOR); SendMessage(GetDlgItem(IDC_ICONSTATIC),STM_SETICON,(WPARAM)m_hIcon,0L); // Label name. SetDlgItemText(IDC_NAMEEDIT,g_ProjectSettings.m_szLabel); // Type. SetDlgItemText(IDC_TYPESTATIC,lngGetString(PROJECT_MIXED)); // Size. unsigned __int64 uiSize = g_ProjectManager.GetProjectSize(); TCHAR szSizeText[32]; FormatBytes(szBuffer,uiSize); lsprintf(szSizeText,_T(" (%I64d Bytes)"),uiSize); lstrcat(szBuffer,szSizeText); SetDlgItemText(IDC_SIZESTATIC,szBuffer); // Contents. unsigned __int64 uiFileCount,uiFolderCount,uiTrackCount; g_ProjectManager.GetProjectContents(uiFileCount,uiFolderCount,uiTrackCount); lsnprintf_s(szBuffer,64,lngGetString(PROJECT_CONTENTS),uiFileCount,uiFolderCount,uiTrackCount); SetDlgItemText(IDC_CONTAINSSTATIC,szBuffer); } LRESULT CProjectPropGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Set edit field length limit. ::SendMessage(GetDlgItem(IDC_NAMEEDIT),EM_SETLIMITTEXT,127,0); switch (g_ProjectManager.GetProjectType()) { case PROJECTTYPE_AUDIO: SetupAudioProject(); break; case PROJECTTYPE_MIXED: SetupMixedProject(); break; case PROJECTTYPE_DATA: SetupDataProject(); break; }; // Translate the window. Translate(); return TRUE; } ================================================ FILE: src/app/dialog/project_prop_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CProjectPropGeneralPage : public CPropertyPageImpl { private: HICON m_hIcon; void SetupDataProject(); void SetupAudioProject(); void SetupMixedProject(); bool Translate(); public: enum { IDD = IDD_PROPPAGE_PROJECTPROPGENERAL }; CProjectPropGeneralPage(); ~CProjectPropGeneralPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CProjectPropGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/project_prop_iso_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_prop_iso_page.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "trans_util.hh" CProjectPropIsoPage::CProjectPropIsoPage() { m_psp.dwFlags |= PSP_HASHELP; } CProjectPropIsoPage::~CProjectPropIsoPage() { } bool CProjectPropIsoPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a projectprop translation section. if (!pLng->EnterSection(_T("projectprop"))) return false; // Translate. TCHAR *szStrValue; int iMaxStaticRight = 0; if (pLng->GetValuePtr(IDC_LEVELSTATIC,szStrValue)) { SetDlgItemText(IDC_LEVELSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_LEVELSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_FORMATSTATIC,szStrValue)) { SetDlgItemText(IDC_FORMATSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_FORMATSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_CHARSETSTATIC,szStrValue)) { SetDlgItemText(IDC_CHARSETSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_CHARSETSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } if (pLng->GetValuePtr(IDC_JOLIETCHECK,szStrValue)) SetDlgItemText(IDC_JOLIETCHECK,szStrValue); if (pLng->GetValuePtr(IDC_JOLIETLONGNAMESCHECK,szStrValue)) SetDlgItemText(IDC_JOLIETLONGNAMESCHECK,szStrValue); if (pLng->GetValuePtr(IDC_OMITVNCHECK,szStrValue)) SetDlgItemText(IDC_OMITVNCHECK,szStrValue); if (pLng->GetValuePtr(IDC_DEEPDIRCHECK,szStrValue)) SetDlgItemText(IDC_DEEPDIRCHECK,szStrValue); // Make sure that the edit controls are not in the way of the statics. if (iMaxStaticRight > 75) { UpdateEditPos(m_hWnd,IDC_LEVELCOMBO,iMaxStaticRight); UpdateEditPos(m_hWnd,IDC_FORMATCOMBO,iMaxStaticRight); } return true; } bool CProjectPropIsoPage::OnApply() { g_ProjectSettings.m_iIsoLevel = m_LevelCombo.GetCurSel(); g_ProjectSettings.m_iIsoFormat = m_FormatCombo.GetCurSel(); g_ProjectSettings.m_IsoCharSet = static_cast(m_CharSetCombo.GetCurSel()); g_ProjectSettings.m_bJoliet = IsDlgButtonChecked(IDC_JOLIETCHECK) == TRUE; g_ProjectSettings.m_bJolietLongNames = IsDlgButtonChecked(IDC_JOLIETLONGNAMESCHECK) == TRUE; g_ProjectSettings.m_bOmitVerNum = IsDlgButtonChecked(IDC_OMITVNCHECK) == TRUE; g_ProjectSettings.m_bDeepDirs = IsDlgButtonChecked(IDC_DEEPDIRCHECK) == TRUE; return true; } void CProjectPropIsoPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/working_with_projects/project_settings.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CProjectPropIsoPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Setup the level combo box. m_LevelCombo = GetDlgItem(IDC_LEVELCOMBO); m_LevelCombo.AddString(lngGetString(PROJECTPROP_ISOLEVEL1)); m_LevelCombo.AddString(lngGetString(PROJECTPROP_ISOLEVEL2)); m_LevelCombo.AddString(lngGetString(PROJECTPROP_ISOLEVEL3)); m_LevelCombo.AddString(lngGetString(PROJECTPROP_ISOLEVEL4)); m_LevelCombo.SetCurSel(g_ProjectSettings.m_iIsoLevel); // Format combo box. m_FormatCombo = GetDlgItem(IDC_FORMATCOMBO); m_FormatCombo.AddString(lngGetString(PROJECTPROP_MODE1)); m_FormatCombo.AddString(lngGetString(PROJECTPROP_MODE2)); m_FormatCombo.SetCurSel(g_ProjectSettings.m_iIsoFormat); // Character set combo box. m_CharSetCombo = GetDlgItem(IDC_CHARSETCOMBO); m_CharSetCombo.AddString(lngGetString(PROJECTPROP_ISO_CHARSET_ISO)); m_CharSetCombo.AddString(_T("DOS")); m_CharSetCombo.AddString(_T("ASCII")); m_CharSetCombo.SetCurSel(g_ProjectSettings.m_IsoCharSet); // Joliet. CheckDlgButton(IDC_JOLIETCHECK,g_ProjectSettings.m_bJoliet); CheckDlgButton(IDC_JOLIETLONGNAMESCHECK,g_ProjectSettings.m_bJolietLongNames); ::EnableWindow(GetDlgItem(IDC_JOLIETLONGNAMESCHECK),g_ProjectSettings.m_bJoliet); // Miscellaneous. CheckDlgButton(IDC_OMITVNCHECK,g_ProjectSettings.m_bOmitVerNum); CheckDlgButton(IDC_DEEPDIRCHECK,g_ProjectSettings.m_bDeepDirs); // Translate the window. Translate(); return TRUE; } LRESULT CProjectPropIsoPage::OnCommand(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { LRESULT lResult = DefWindowProc(); if (HIWORD(wParam) == BN_CLICKED) { // IDC_JOLIETCHECK clicked? if (LOWORD(wParam) == IDC_JOLIETCHECK) { bool bJoliet = IsDlgButtonChecked(IDC_JOLIETCHECK) == TRUE; ::EnableWindow(GetDlgItem(IDC_JOLIETLONGNAMESCHECK),bJoliet); } } bHandled = false; return lResult; } ================================================ FILE: src/app/dialog/project_prop_iso_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CProjectPropIsoPage : public CPropertyPageImpl { private: CComboBox m_LevelCombo; CComboBox m_FormatCombo; CComboBox m_CharSetCombo; bool Translate(); public: enum { IDD = IDD_PROPPAGE_PROJECTPROPISO }; CProjectPropIsoPage(); ~CProjectPropIsoPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CProjectPropIsoPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_COMMAND,OnCommand) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnCommand(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/project_prop_udf_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_prop_udf_page.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "trans_util.hh" CProjectPropUdfPage::CProjectPropUdfPage() { m_psp.dwFlags |= PSP_HASHELP; } CProjectPropUdfPage::~CProjectPropUdfPage() { } bool CProjectPropUdfPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a projectprop translation section. if (!pLng->EnterSection(_T("projectprop"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDC_VERSIONSTATIC,szStrValue)) SetDlgItemText(IDC_VERSIONSTATIC,szStrValue); return true; } bool CProjectPropUdfPage::OnApply() { return true; } void CProjectPropUdfPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/working_with_projects/project_settings.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } LRESULT CProjectPropUdfPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Setup the version combo box. CComboBox VersionCombo = GetDlgItem(IDC_VERSIONCOMBO); VersionCombo.AddString(_T("1.02")); VersionCombo.SetCurSel(0); // Translate the window. Translate(); return TRUE; } ================================================ FILE: src/app/dialog/project_prop_udf_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CProjectPropUdfPage : public CPropertyPageImpl { private: bool Translate(); public: enum { IDD = IDD_PROPPAGE_PROJECTPROPUDF }; CProjectPropUdfPage(); ~CProjectPropUdfPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CProjectPropUdfPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/read_options_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "read_options_page.hh" #include "ctrl_messages.hh" #include "string_table.hh" #include "lang_util.hh" #include "settings.hh" #include "trans_util.hh" #include "core2.hh" #include "core2_util.hh" #include "version.hh" #include "infrarecorder.hh" #include "visual_styles.hh" CReadOptionsPage::CReadOptionsPage(bool bEnableClone,bool bEnableSpeed) { m_bEnableClone = bEnableClone; m_bEnableSpeed = bEnableSpeed; m_hRefreshIcon = NULL; m_hRefreshImageList = NULL; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TITLE_READ,szStrValue)) SetTitle(szStrValue); } } m_psp.dwFlags |= PSP_HASHELP; } CReadOptionsPage::~CReadOptionsPage() { if (m_hRefreshImageList != NULL) ImageList_Destroy(m_hRefreshImageList); if (m_hRefreshIcon != NULL) DestroyIcon(m_hRefreshIcon); } bool CReadOptionsPage::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a burn translation section. if (!pLng->EnterSection(_T("read"))) return false; // Translate. TCHAR *szStrValue; int iMaxStaticRight = 0; if (pLng->GetValuePtr(IDC_NOREADERRCHECK,szStrValue)) SetDlgItemText(IDC_NOREADERRCHECK,szStrValue); if (pLng->GetValuePtr(IDC_READSUBCHANNELCHECK,szStrValue)) SetDlgItemText(IDC_READSUBCHANNELCHECK,szStrValue); if (pLng->GetValuePtr(IDC_READSPEEDSTATIC,szStrValue)) { SetDlgItemText(IDC_READSPEEDSTATIC,szStrValue); // Update the static width if necessary. int iStaticRight = UpdateStaticWidth(m_hWnd,IDC_READSPEEDSTATIC,szStrValue); if (iStaticRight > iMaxStaticRight) iMaxStaticRight = iStaticRight; } // Make sure that the edit/combo controls are not in the way of the statics. if (iMaxStaticRight > 75) UpdateEditPos(m_hWnd,IDC_READSPEEDCOMBO,iMaxStaticRight,true); return true; } bool CReadOptionsPage::OnApply() { // Remember the configuration. g_ReadSettings.m_bIgnoreErr = IsDlgButtonChecked(IDC_NOREADERRCHECK) == TRUE; g_ReadSettings.m_bClone = IsDlgButtonChecked(IDC_READSUBCHANNELCHECK) == TRUE; g_ReadSettings.m_iReadSpeed = m_ReadSpeedCombo.GetItemData(m_ReadSpeedCombo.GetCurSel()); return true; } void CReadOptionsPage::OnHelp() { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/read_options.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); } void CReadOptionsPage::UpdateSpeeds() { ckmmc::Device &Device = *reinterpret_cast(::SendMessage(GetParent(),WM_GETDEVICE,1,0)); // Maximum read speed. m_ReadSpeedCombo.ResetContent(); m_ReadSpeedCombo.AddString(lngGetString(MISC_MAXIMUM)); m_ReadSpeedCombo.SetItemData(0,0xFFFFFFFF); m_ReadSpeedCombo.SetCurSel(0); // Get current profile. ckmmc::Device::Profile Profile = Device.profile(); if (Profile != ckmmc::Device::ckPROFILE_NONE) { const std::vector &ReadSpeeds = Device.read_speeds(); std::vector::const_iterator it; for (it = ReadSpeeds.begin(); it != ReadSpeeds.end(); it++) { m_ReadSpeedCombo.AddString(ckmmc::util::kb_to_disp_speed(*it,Profile).c_str()); m_ReadSpeedCombo.SetItemData(m_ReadSpeedCombo.GetCount() - 1, static_cast(ckmmc::util::kb_to_human_speed(*it, ckmmc::Device::ckPROFILE_CDR))); } } } void CReadOptionsPage::CheckMedia() { if (m_bEnableSpeed) { UpdateSpeeds(); } else { m_ReadSpeedCombo.ResetContent(); m_ReadSpeedCombo.AddString(lngGetString(MISC_AUTO)); m_ReadSpeedCombo.SetCurSel(0); } } LRESULT CReadOptionsPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { m_ReadSpeedCombo = GetDlgItem(IDC_READSPEEDCOMBO); CheckDlgButton(IDC_NOREADERRCHECK,g_ReadSettings.m_bIgnoreErr); // Enable/disable options. if (!m_bEnableClone) { ::EnableWindow(GetDlgItem(IDC_READSUBCHANNELCHECK),FALSE); CheckDlgButton(IDC_READSUBCHANNELCHECK,m_bCloneCheck); } else { CheckDlgButton(IDC_READSUBCHANNELCHECK,g_ReadSettings.m_bClone); } if (!m_bEnableSpeed) { ::EnableWindow(GetDlgItem(IDC_READSPEEDSTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_READSPEEDCOMBO),FALSE); } // Translate the window. Translate(); return TRUE; } LRESULT CReadOptionsPage::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if ((BOOL)wParam == TRUE) CheckMedia(); bHandled = FALSE; return 0; } LRESULT CReadOptionsPage::OnCheckMedia(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CheckMedia(); bHandled = FALSE; return 0; } void CReadOptionsPage::SetCloneMode(bool bEnable) { m_bCloneCheck = bEnable; if (IsWindow()) CheckDlgButton(IDC_READSUBCHANNELCHECK,bEnable); } ================================================ FILE: src/app/dialog/read_options_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "ctrl_messages.hh" class CReadOptionsPage : public CPropertyPageImpl { private: bool m_bEnableClone; bool m_bEnableSpeed; bool m_bCloneCheck; // The initial state of the read subchannel data. HICON m_hRefreshIcon; HIMAGELIST m_hRefreshImageList; CComboBox m_ReadSpeedCombo; bool Translate(); void UpdateSpeeds(); void CheckMedia(); public: enum { IDD = IDD_PROPPAGE_READOPTIONS }; CReadOptionsPage(bool bEnableClone,bool bEnableSpeed); ~CReadOptionsPage(); bool OnApply(); void OnHelp(); BEGIN_MSG_MAP(CReadOptionsPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) MESSAGE_HANDLER(WM_CHECKMEDIA,OnCheckMedia) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnCheckMedia(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); void SetCloneMode(bool bEnable); }; ================================================ FILE: src/app/dialog/save_tracks_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "save_tracks_dlg.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" CSaveTracksDlg::CSaveTracksDlg() { m_pEncoder = NULL; } CSaveTracksDlg::~CSaveTracksDlg() { } bool CSaveTracksDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a edittrack translation section. if (!pLng->EnterSection(_T("savetracks"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDD_SAVETRACKSDLG,szStrValue)) // Title. SetWindowText(szStrValue); if (pLng->GetValuePtr(IDC_TARGETSTATIC,szStrValue)) SetDlgItemText(IDC_TARGETSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_AUDIOFORMATSTATIC,szStrValue)) SetDlgItemText(IDC_AUDIOFORMATSTATIC,szStrValue); if (pLng->GetValuePtr(IDC_AUDIOFORMATBUTTON,szStrValue)) SetDlgItemText(IDC_AUDIOFORMATBUTTON,szStrValue); return true; } LRESULT CSaveTracksDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); // Setup the target edit control. ::SendMessage(GetDlgItem(IDC_TARGETEDIT),EM_SETLIMITTEXT,MAX_PATH - 1,0); SetDlgItemText(IDC_TARGETEDIT,g_SaveTracksSettings.m_szTarget); // Setup the audio format combo box. m_AudioFormatCombo = GetDlgItem(IDC_AUDIOFORMATCOMBO); m_AudioFormatCombo.ResetContent(); // The first item is always wave. Not the wave encoder, but the cdrtools // default encoder. m_AudioFormatCombo.AddString(_T("Wave")); for (unsigned int i = 0; i < g_CodecManager.m_Codecs.size(); i++) { // Skip any installed wave codecs since cdrtools has its own. if (!lstrcmp(g_CodecManager.m_Codecs[i]->irc_string(IRC_STR_FILEEXT),_T(".wav"))) continue; if (g_CodecManager.m_Codecs[i]->irc_capabilities() & IRC_HAS_ENCODER) { m_AudioFormatCombo.AddString(g_CodecManager.m_Codecs[i]->irc_string(IRC_STR_ENCODER)); m_AudioFormatCombo.SetItemData(m_AudioFormatCombo.GetCount() - 1,(DWORD_PTR)g_CodecManager.m_Codecs[i]); } } m_AudioFormatCombo.SetCurSel(0); ::EnableWindow(GetDlgItem(IDC_AUDIOFORMATBUTTON),FALSE); // Translate the window. Translate(); return TRUE; } LRESULT CSaveTracksDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Target folder. TCHAR szFolderPath[MAX_PATH]; GetDlgItemText(IDC_TARGETEDIT,szFolderPath,MAX_PATH - 1); if (szFolderPath == NULL || lstrlen(szFolderPath) < 3 || szFolderPath[1] != ':') { MessageBox(lngGetString(ERROR_TARGETFOLDER),lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return FALSE; } // Check if the target path exist. const ckcore::Path Path(szFolderPath); if (!ckcore::Directory::exist(Path)) { if (MessageBox(lngSlowFormatStr(CONFIRM_CREATE_DIR_PATH,szFolderPath).c_str(), lngGetString(GENERAL_QUESTION), MB_YESNO | MB_ICONQUESTION) != IDYES) { return FALSE; } if (!ckcore::Directory::create(Path)) { MessageBox(lngSlowFormatStr(CANNOT_CREATE_DIR_PATH,szFolderPath).c_str(), lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return FALSE; } } lstrcpy(g_SaveTracksSettings.m_szTarget,szFolderPath); // Encoder. if (m_AudioFormatCombo.GetCurSel() == 0) m_pEncoder = NULL; else m_pEncoder = (CCodec *)m_AudioFormatCombo.GetItemData(m_AudioFormatCombo.GetCurSel()); EndDialog(wID); return FALSE; } LRESULT CSaveTracksDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } LRESULT CSaveTracksDlg::OnAudioFormatChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (m_AudioFormatCombo.GetCurSel() == 0) { ::EnableWindow(GetDlgItem(IDC_AUDIOFORMATBUTTON),FALSE); } else { CCodec *pEncoder = (CCodec *)m_AudioFormatCombo.GetItemData(m_AudioFormatCombo.GetCurSel()); ::EnableWindow(GetDlgItem(IDC_AUDIOFORMATBUTTON),pEncoder->irc_capabilities() & IRC_HAS_CONFIG); } return 0; } LRESULT CSaveTracksDlg::OnClickedAudioFormatButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // This should never happen. if (m_AudioFormatCombo.GetCurSel() == 0) return 0; CCodec *pEncoder = (CCodec *)m_AudioFormatCombo.GetItemData(m_AudioFormatCombo.GetCurSel()); pEncoder->irc_encode_config(); return 0; } LRESULT CSaveTracksDlg::OnClickedBrowseButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CFolderDialog FolderDialog(m_hWnd,lngGetString(MISC_SPECIFYTRACKFOLDER),BIF_NEWDIALOGSTYLE | BIF_RETURNONLYFSDIRS); if (FolderDialog.DoModal() == IDOK) SetDlgItemText(IDC_TARGETEDIT,FolderDialog.GetFolderPath()); return 0; } CCodec *CSaveTracksDlg::GetEncoder() { return m_pEncoder; } ================================================ FILE: src/app/dialog/save_tracks_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "infrarecorder.hh" class CSaveTracksDlg : public CDialogImpl { private: CComboBox m_AudioFormatCombo; CCodec *m_pEncoder; bool Translate(); public: enum { IDD = IDD_SAVETRACKSDLG }; CSaveTracksDlg(); ~CSaveTracksDlg(); BEGIN_MSG_MAP(CSaveTracksDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) COMMAND_HANDLER(IDC_AUDIOFORMATCOMBO,CBN_SELCHANGE,OnAudioFormatChange) COMMAND_HANDLER(IDC_AUDIOFORMATBUTTON,BN_CLICKED,OnClickedAudioFormatButton) COMMAND_HANDLER(IDC_BROWSEBUTTON,BN_CLICKED,OnClickedBrowseButton) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnAudioFormatChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnClickedAudioFormatButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnClickedBrowseButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); CCodec *GetEncoder(); }; ================================================ FILE: src/app/dialog/simple_progress_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "string_table.hh" #include "lang_util.hh" #include "device_util.hh" #include "settings.hh" #include "version.hh" #include "simple_progress_dlg.hh" static const int SUBITEM_TEXT = 1; CSimpleProgressDlg::CSimpleProgressDlg() : m_pProcess(NULL),m_bAppMode(false), m_bRealMode(false),m_bCancelled(false),m_hWndHost(NULL) { // Load the icons. m_hListImageList = ImageList_Create(16,16,ILC_COLOR32,0,4); ImageList_AddIcon(m_hListImageList,LoadIcon(NULL,IDI_INFORMATION)); ImageList_AddIcon(m_hListImageList,LoadIcon(NULL,IDI_WARNING)); ImageList_AddIcon(m_hListImageList,LoadIcon(NULL,IDI_ERROR)); ImageList_AddIcon(m_hListImageList,LoadIcon(NULL,IDI_WINLOGO)); SMOKE_INIT } CSimpleProgressDlg::~CSimpleProgressDlg() { if (m_hListImageList != NULL) ImageList_Destroy(m_hListImageList); } BOOL CSimpleProgressDlg::PreTranslateMessage(MSG *pMsg) { return CWindow::IsDialogMessage(pMsg); } BOOL CSimpleProgressDlg::OnIdle() { return FALSE; } bool CSimpleProgressDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a progress translation section. if (!pLng->EnterSection(_T("progress"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDCANCEL,szStrValue)) SetDlgItemText(IDCANCEL,szStrValue); if (pLng->GetValuePtr(IDC_RELOADBUTTON,szStrValue)) SetDlgItemText(IDC_RELOADBUTTON,szStrValue); return true; } void CSimpleProgressDlg::AttachProcess(ckcore::Process *pProcess) { m_pProcess = pProcess; } void CSimpleProgressDlg::AttachHost(HWND hWndHost) { m_hWndHost = hWndHost; } void CSimpleProgressDlg::SetAppMode(bool bAppMode) { m_bAppMode = bAppMode; } void CSimpleProgressDlg::SetRealMode(bool bRealMode) { m_bRealMode = bRealMode; } void CSimpleProgressDlg::set_status(const TCHAR *szStatus,...) { // Prepare the string. TCHAR szStatusStr[256]; lstrcpy(szStatusStr,lngGetString(PROGRESS_STATUS)); unsigned int uiFreeSpace = sizeof(szStatusStr)/sizeof(TCHAR) - lstrlen(szStatusStr) - 1; if ((unsigned int)lstrlen(szStatus) > uiFreeSpace) lstrncat(szStatusStr,szStatus,uiFreeSpace); else lstrcat(szStatusStr,szStatus); // Parse the variable argument list. va_list args; va_start(args,szStatus); _vsnwprintf(m_szStringBuffer,PROGRESS_STRINGBUFFER_SIZE - 1,szStatusStr,args); SetDlgItemText(IDC_STATUSSTATIC,m_szStringBuffer); } void CSimpleProgressDlg::notify(ckcore::Progress::MessageType Type,const TCHAR *szMessage,...) { int iItemIndex = m_ListView.GetItemCount(); // Time. SYSTEMTIME st; GetLocalTime(&st); TCHAR szTime[9]; // xx:yy:zz lsprintf(szTime,_T("%.2d:%.2d:%.2d"),st.wHour,st.wMinute,st.wSecond); szTime[8] = '\0'; // Convert the log type to an index. int iImageIndex = 0; switch (Type) { case ckcore::Progress::ckINFORMATION: iImageIndex = 0; break; case ckcore::Progress::ckWARNING: iImageIndex = 1; break; case ckcore::Progress::ckERROR: iImageIndex = 2; break; case ckcore::Progress::ckEXTERNAL: iImageIndex = 3; break; } m_ListView.AddItem(iItemIndex,0,szTime,iImageIndex); // Parse the variable argument list. va_list args; va_start(args,szMessage); _vsnwprintf(m_szStringBuffer,PROGRESS_STRINGBUFFER_SIZE - 1,szMessage,args); m_ListView.AddItem(iItemIndex,SUBITEM_TEXT,m_szStringBuffer); m_ListView.SetColumnWidth(SUBITEM_TEXT,LVSCW_AUTOSIZE); m_ListView.EnsureVisible(iItemIndex,false); } bool CSimpleProgressDlg::cancelled() { return m_bCancelled; } void CSimpleProgressDlg::SetDevice(ckmmc::Device &Device) { ckcore::tstring DeviceStr = lngGetString(PROGRESS_DEVICE); DeviceStr += NDeviceUtil::GetDeviceName(Device); SetDlgItemText(IDC_DEVICESTATIC,DeviceStr.c_str()); } void CSimpleProgressDlg::NotifyCompleted() { ::EnableWindow(GetDlgItem(IDOK),true); SendMessage(WM_NEXTDLGCTL,(WPARAM)::GetDlgItem(m_hWnd,IDOK),0); // Change default focus to the OK button. ::EnableWindow(GetDlgItem(IDCANCEL),false); if (m_bCancelled) { set_status(lngGetString(PROGRESS_CANCELED)); notify(ckcore::Progress::ckWARNING,lngGetString(PROGRESS_CANCELED)); } SMOKE_STOP } void CSimpleProgressDlg::AllowReload() { ::ShowWindow(GetDlgItem(IDC_RELOADBUTTON),SW_SHOW); } void CSimpleProgressDlg::AllowCancel(bool bAllow) { ::EnableWindow(GetDlgItem(IDCANCEL),bAllow); } void CSimpleProgressDlg::Reset() { m_bRealMode = false; m_bCancelled = false; } bool CSimpleProgressDlg::RequestNextDisc() { return lngMessageBox(m_hWnd,INFO_NEXTCOPY,GENERAL_INFORMATION,MB_OKCANCEL | MB_ICONINFORMATION) == IDOK; } void CSimpleProgressDlg::StartSmoke() { SMOKE_START } LRESULT CSimpleProgressDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { DlgResize_Init(); CenterWindow(GetParent()); // If we're in application mode, add a minimize button to the window. // UPDATE: This does not work, nor is it a good idea regarding the smoke effect. /*if (m_bAppMode) ModifyStyle(0,WS_MINIMIZEBOX,0);*/ // Initialize the list view. m_ListView = GetDlgItem(IDC_MESSAGELIST); m_ListView.SetImageList(m_hListImageList,LVSIL_NORMAL); m_ListView.SetImageList(m_hListImageList,LVSIL_SMALL); m_ListView.SetExtendedListViewStyle(LVS_EX_FULLROWSELECT); m_ListView.AddColumn(lngGetString(COLUMN_TIME),0); m_ListView.SetColumnWidth(0,70); m_ListView.AddColumn(lngGetString(COLUMN_EVENT),1); m_ListView.SetColumnWidth(1,350); // Disable the OK button. ::EnableWindow(GetDlgItem(IDOK),false); ::EnableWindow(GetDlgItem(IDCANCEL),true); // Translate the window. Translate(); return TRUE; } LRESULT CSimpleProgressDlg::OnReload(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Send a CR-LF message to inform CD-tools that the drive has been reloaded. if (m_pProcess != NULL) m_pProcess->write("\r\n",2); // Hide the reload button. ::ShowWindow(GetDlgItem(IDC_RELOADBUTTON),SW_HIDE); return FALSE; } LRESULT CSimpleProgressDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Re-enable the main window. //g_MainFrame->EnableWindow(true); if (::IsWindow(m_hWndHost)) ::EnableWindow(m_hWndHost,true); DestroyWindow(); // If we're in application mode we post a quit message. if (m_bAppMode) ::PostQuitMessage(wID); return FALSE; } LRESULT CSimpleProgressDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Make sure that we're allowed to cancel. if (!::IsWindowEnabled(GetDlgItem(IDCANCEL))) return TRUE; // If we're in real mode we dispay a warning message informing the user that // aborting might permanently damage the CD. if (m_bRealMode) { if (lngMessageBox(m_hWnd,CONFIRM_WRITECANCEL,GENERAL_WARNING,MB_YESNO | MB_ICONWARNING) == IDNO) return TRUE; } m_bCancelled = true; if (m_pProcess != NULL) m_pProcess->kill(); // Hide the reload button. ::ShowWindow(GetDlgItem(IDC_RELOADBUTTON),SW_HIDE); return TRUE; } LRESULT CSimpleProgressDlg::OnListViewDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { ATLASSERT(iCtrlID == IDC_MESSAGELIST); LPNMITEMACTIVATE pItemActivate = (LPNMITEMACTIVATE)pNMH; _bstr_t LineText; m_ListView.GetItemText(pItemActivate->iItem,SUBITEM_TEXT,LineText.GetBSTR()); MessageBox(LineText,_T("Log line"),MB_OK | MB_ICONINFORMATION); bHandled = TRUE; return 0; } ================================================ FILE: src/app/dialog/simple_progress_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include "resource.h" #include "advanced_progress.hh" #include "effects.hh" #include "version.hh" class CSimpleProgressDlg : public CDialogImpl, public CDialogResize, public CAdvancedProgress,public CMessageFilter, public CIdleHandler { private: HIMAGELIST m_hListImageList; CListViewCtrl m_ListView; ckcore::Process *m_pProcess; bool m_bAppMode; bool m_bRealMode; bool m_bCancelled; HWND m_hWndHost; bool Translate(); public: enum { IDD = IDD_SIMPLEPROGRESSDLG }; CSimpleProgressDlg(); ~CSimpleProgressDlg(); virtual BOOL PreTranslateMessage(MSG *pMsg); virtual BOOL OnIdle(); void AttachProcess(ckcore::Process *pProcess); void AttachHost(HWND hWndHost); void SetAppMode(bool bAppMode); void SetRealMode(bool bRealMode); // ckcore::Progress. void set_status(const TCHAR *szStatus,...); void notify(ckcore::Progress::MessageType Type,const TCHAR *szMessage,...); bool cancelled(); void SetDevice(ckmmc::Device &Device); void NotifyCompleted(); void AllowReload(); void AllowCancel(bool bAllow); void Reset(); bool RequestNextDisc(); void StartSmoke(); BEGIN_MSG_MAP(CSimpleProgressDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDC_RELOADBUTTON,OnReload) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) NOTIFY_HANDLER(IDC_MESSAGELIST,NM_DBLCLK,OnListViewDblClick) SMOKE_EVENTS CHAIN_MSG_MAP(CDialogResize) END_MSG_MAP() // Resize maps. BEGIN_DLGRESIZE_MAP(CSimpleProgressDlg) DLGRESIZE_CONTROL(IDC_STATUSSTATIC,DLSZ_SIZE_X) DLGRESIZE_CONTROL(IDC_MESSAGELIST,DLSZ_SIZE_X | DLSZ_SIZE_Y) DLGRESIZE_CONTROL(IDC_BEVELSTATIC,DLSZ_SIZE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_DEVICESTATIC,DLSZ_SIZE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDOK,DLSZ_MOVE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDCANCEL,DLSZ_MOVE_X | DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_RELOADBUTTON,DLSZ_MOVE_X | DLSZ_MOVE_Y) END_DLGRESIZE_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnReload(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnListViewDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); SMOKE_IMPL }; extern CSimpleProgressDlg * g_pSimpleProgressDlg; ================================================ FILE: src/app/dialog/splash_window.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "resource.h" #include "infrarecorder.hh" #include "string_table.hh" #include "lang_util.hh" #include "splash_window.hh" CSplashWindow::CSplashWindow() { m_hTextBkBrush = ::CreateSolidBrush(SPLASHWINDOW_TEXTBKCOLOR); // Load the function dynamically. HMODULE hUser32 = GetModuleHandle(_T("USER32.DLL")); m_pUpdateLayeredWindow = (tUpdateLayeredWindow)GetProcAddress(hUser32,"UpdateLayeredWindow"); // Load a 32-bit transparent bitmap for Windows 2000 and newer systems. if (m_pUpdateLayeredWindow != NULL) LoadBitmap(); } CSplashWindow::~CSplashWindow() { ::DeleteObject(m_hTextBkBrush); } LRESULT CSplashWindow::OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { SIZE sSplashBitmap; m_SplashBitmap.GetSize(sSplashBitmap); SetWindowPos(HWND_TOPMOST,0,0,sSplashBitmap.cx,sSplashBitmap.cy,SWP_NOMOVE); CenterWindow(HWND_DESKTOP); // For per-pixel alpha transparency the window needs to be layered. if (m_pUpdateLayeredWindow != NULL) ModifyStyleEx(0,WS_EX_LAYERED); return 0; } LRESULT CSplashWindow::OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CPaintDC dc(m_hWnd); if (m_pUpdateLayeredWindow == NULL) return 0; RECT rcClient; GetClientRect(&rcClient); HDC hMemDC = CreateCompatibleDC(dc); HBITMAP hOldBitmap = (HBITMAP)SelectObject(hMemDC,m_SplashBitmap); DrawText(hMemDC); DrawBitmap(dc,hMemDC); SelectObject(hMemDC,hOldBitmap); ReleaseDC(dc); ReleaseDC(hMemDC); return 0; } void CSplashWindow::DrawBitmap(HDC hScreenDC,HDC hMemDC) { SIZE sSplashBitmap; m_SplashBitmap.GetSize(sSplashBitmap); // Calculate window dimensions. RECT rcWindow; GetWindowRect(&rcWindow); POINT ptWindowPos; ptWindowPos.x = rcWindow.left; ptWindowPos.y = rcWindow.top; BLENDFUNCTION bfPixelFunction = { AC_SRC_OVER,0,255,AC_SRC_ALPHA }; POINT ptSource = { 0,0 }; m_pUpdateLayeredWindow(m_hWnd,hScreenDC,&ptWindowPos,&sSplashBitmap,hMemDC,&ptSource,0,&bfPixelFunction,ULW_ALPHA); } void CSplashWindow::DrawText(HDC hDC) { HFONT hOldFont = (HFONT)SelectObject(hDC,AtlGetDefaultGuiFont()); // Calculate the text height. SIZE sTextSize; GetTextExtentPoint32(hDC,m_InfoText.c_str(), static_cast(m_InfoText.size()),&sTextSize); RECT rcText = { 33,125,280,125 + sTextSize.cy }; // Do the actual drawing. FillRect(hDC,&rcText,m_hTextBkBrush); ::SetBkColor(hDC,SPLASHWINDOW_TEXTBKCOLOR); ::SetTextColor(hDC,::GetSysColor(COLOR_WINDOWTEXT)); ::DrawText(hDC,m_InfoText.c_str(), static_cast(m_InfoText.size()),&rcText, DT_LEFT | DT_END_ELLIPSIS | DT_SINGLELINE); SelectObject(hDC,hOldFont); // Get bitmap information. BITMAP bmpInfo; m_SplashBitmap.GetBitmap(&bmpInfo); // Since the regular GDI functions (with a few exceptions) clear the alpha bit // when they are used we need to set it, since we don't want to draw // transparent text. unsigned char *pDataBits = (unsigned char *)bmpInfo.bmBits; int iStart = bmpInfo.bmHeight - rcText.bottom; int iEnd = bmpInfo.bmHeight - rcText.top; for (int y = iStart; y < iEnd; y++) { unsigned char *pPixel = pDataBits + bmpInfo.bmWidth * 4 * y; pPixel += 4 * rcText.left; for (int x = rcText.left; x < rcText.right; x++) { pPixel[3] = 0xFF; pPixel += 4; } } } void CSplashWindow::SetInfoText(const TCHAR *szInfoText) { m_InfoText = szInfoText; // Force redraw. InvalidateRect(NULL); // Process the message queue. ProcessMessages(); } void CSplashWindow::LoadBitmap() { // Load the bitmap. HBITMAP hBitmap = (HBITMAP)LoadImage(_Module.GetModuleInstance(),MAKEINTRESOURCE(IDB_SPLASHBITMAP), IMAGE_BITMAP,0,0,LR_CREATEDIBSECTION); m_SplashBitmap.Attach(hBitmap); // Precaclulate multiply the transparency. BITMAP bmpInfo; m_SplashBitmap.GetBitmap(&bmpInfo); unsigned char *pDataBits = (unsigned char *)bmpInfo.bmBits; for (int y = 0; y < bmpInfo.bmHeight; y++) { unsigned char *pPixel = pDataBits + bmpInfo.bmWidth * 4 * y; for (int x = 0; x < bmpInfo.bmWidth; x++) { pPixel[0] = pPixel[0] * pPixel[3] / 255; pPixel[1] = pPixel[1] * pPixel[3] / 255; pPixel[2] = pPixel[2] * pPixel[3] / 255; pPixel += 4; } } } void CSplashWindow::event_status(ckmmc::DeviceManager::ScanCallback::Status Status) { if (Status == ckmmc::DeviceManager::ScanCallback::ckEVENT_DEV_SCAN) SetInfoText(lngGetString(INIT_SCANBUS)); else if (Status == ckmmc::DeviceManager::ScanCallback::ckEVENT_DEV_CAP) SetInfoText(lngGetString(INIT_LOADCAPABILITIES)); } bool CSplashWindow::event_device(ckmmc::Device::Address &Addr) { return true; } void CSplashWindow::SafeCreate() { Create(HWND_DESKTOP,CWindow::rcDefault); } void CSplashWindow::SafeDestroy() { DestroyWindow(); } ================================================ FILE: src/app/dialog/splash_window.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #define SPLASHWINDOW_TEXTBKCOLOR RGB(255,255,255) #if (_WIN32_WINNT < 0x0500) #define WS_EX_LAYERED 0x00080000 #define ULW_ALPHA 0x00000002 #endif typedef BOOL (WINAPI *tUpdateLayeredWindow)(HWND hWnd,HDC hdcDst,POINT *pptDst, SIZE *psize,HDC hdcSrc,POINT *pptSrc, COLORREF crKey,BLENDFUNCTION *pblend, DWORD dwFlags); class CSplashWindow : public CWindowImpl >, public ckmmc::DeviceManager::ScanCallback { private: CBitmap m_SplashBitmap; HBRUSH m_hTextBkBrush; ckcore::tstring m_InfoText; tUpdateLayeredWindow m_pUpdateLayeredWindow; void DrawBitmap(HDC hScreenDC,HDC hMemDC); void DrawText(HDC hDC); void LoadBitmap(); void SetInfoText(const TCHAR *szInfoText); /* * ckmmc::DeviceManager::ScanCallback interface. */ void event_status(ckmmc::DeviceManager::ScanCallback::Status Status); bool event_device(ckmmc::Device::Address &Addr); public: CSplashWindow(); ~CSplashWindow(); BEGIN_MSG_MAP(CSplashWindow) MESSAGE_HANDLER(WM_CREATE,OnCreate) MESSAGE_HANDLER(WM_PAINT,OnPaint) END_MSG_MAP() LRESULT OnCreate(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnPaint(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); void SafeCreate(); void SafeDestroy(); }; ================================================ FILE: src/app/dialog/tracks_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "string_table.hh" #include "scsi.hh" #include "wait_dlg.hh" #include "version.hh" #include "progress_dlg.hh" #include "infrarecorder.hh" #include "device_util.hh" #include "core.hh" #include "core2.hh" #include "lang_util.hh" #include "settings.hh" #include "save_tracks_dlg.hh" #include "tracks_dlg.hh" CTracksDlg::CTracksDlg(bool bAppMode) { m_bAppMode = bAppMode; m_hListImageList = NULL; m_hToolBarImageList = NULL; m_pEncoder = NULL; } CTracksDlg::~CTracksDlg() { if (m_hListImageList) ImageList_Destroy(m_hListImageList); if (m_hToolBarImageList) ImageList_Destroy(m_hToolBarImageList); } bool CTracksDlg::Translate() { if (g_LanguageSettings.m_pLngProcessor == NULL) return false; CLngProcessor *pLng = g_LanguageSettings.m_pLngProcessor; // Make sure that there is a tracks translation section. if (!pLng->EnterSection(_T("tracks"))) return false; // Translate. TCHAR *szStrValue; if (pLng->GetValuePtr(IDD_TRACKSDLG,szStrValue)) // Title. SetWindowText(szStrValue); if (pLng->GetValuePtr(IDOK,szStrValue)) SetDlgItemText(IDOK,szStrValue); if (pLng->GetValuePtr(IDC_HELPBUTTON,szStrValue)) SetDlgItemText(IDC_HELPBUTTON,szStrValue); if (pLng->GetValuePtr(IDC_DRIVESTATIC,szStrValue)) SetDlgItemText(IDC_DRIVESTATIC,szStrValue); return true; } unsigned long CTracksDlg::MSFToLBA(unsigned long ulMin,unsigned long ulSec, unsigned long ulFrame) { return ((ulMin * 60 * 75) + (ulSec * 75) + ulFrame - 150); } void CTracksDlg::InitListImageList() { m_hListImageList = ImageList_Create(16,16,ILC_COLOR32,4,5); HICON hIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_DATAICON),IMAGE_ICON,16,16,LR_LOADTRANSPARENT); ImageList_AddIcon(m_hListImageList,hIcon); DestroyIcon(hIcon); hIcon = (HICON)LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDI_AUDIOICON),IMAGE_ICON,16,16,LR_LOADTRANSPARENT); ImageList_AddIcon(m_hListImageList,hIcon); DestroyIcon(hIcon); } void CTracksDlg::InitToolBarImageList() { // Create the image list. HBITMAP hBitmap; // Get color depth (minimum requirement is 32-bits for alpha blended images). int iBitsPixel = GetDeviceCaps(::GetDC(HWND_DESKTOP),BITSPIXEL); if (g_WinVer.m_ulMajorCCVersion >= 6 && iBitsPixel >= 32) { hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_TRACKTOOLBARBITMAP)); m_hToolBarImageList = ImageList_Create(16,16,ILC_COLOR32,0,3); ImageList_Add(m_hToolBarImageList,hBitmap,NULL); } else { hBitmap = LoadBitmap(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDB_TRACKTOOLBARBITMAP_)); m_hToolBarImageList = ImageList_Create(16,16,ILC_COLOR32 | ILC_MASK,0,3); ImageList_AddMasked(m_hToolBarImageList,hBitmap,RGB(255,0,255)); } DeleteObject(hBitmap); } void CTracksDlg::AddToolBarSeparator() { TBBUTTON tbButton; tbButton.fsState = TBSTATE_ENABLED; tbButton.fsStyle = TBSTYLE_SEP; tbButton.iBitmap = 0; tbButton.idCommand = 0; tbButton.iString = 0; tbButton.dwData = 0; m_ToolBar.InsertButton(m_ToolBar.GetButtonCount(),&tbButton); } void CTracksDlg::AddToolBarButton(int iCommand,int iBitmap) { TBBUTTON tbButton; tbButton.fsState = TBSTATE_ENABLED; tbButton.fsStyle = TBSTYLE_BUTTON; tbButton.iBitmap = iBitmap; tbButton.idCommand = iCommand; tbButton.iString = 0; tbButton.dwData = 0; m_ToolBar.InsertButton(m_ToolBar.GetButtonCount(),&tbButton); } void CTracksDlg::CreateToolBarCtrl() { RECT rcListView; ::GetWindowRect(GetDlgItem(IDC_TRACKLIST),&rcListView); ScreenToClient(&rcListView); RECT rcToolBar = { 0,0,100,100 }; m_ToolBar.Create(m_hWnd,rcToolBar,NULL,ATL_SIMPLE_TOOLBAR_PANE_STYLE,NULL); m_ToolBar.SetImageList(m_hToolBarImageList); m_ToolBar.SetButtonStructSize(); // Create the buttons. AddToolBarButton(ID_TRACK_READ,0); AddToolBarButton(ID_TRACK_VERIFY,1); AddToolBarSeparator(); AddToolBarButton(ID_TRACK_ERASE,2); // Update the toolbar position. m_ToolBar.SetWindowPos(NULL, rcListView.left, rcListView.bottom + 4, rcListView.right - rcListView.left, HIWORD(m_ToolBar.GetButtonSize()),0); } LRESULT CTracksDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); // Add the window to the task bar and add a minimize button to the dialog if // the windows is in application mode. /*if (m_bAppMode) { ModifyStyle(WS_POPUPWINDOW | WS_DLGFRAME | DS_MODALFRAME,(WS_OVERLAPPEDWINDOW & ~WS_MAXIMIZEBOX) | WS_OVERLAPPED,0); ModifyStyleEx(WS_EX_DLGMODALFRAME,WS_EX_APPWINDOW,0); // Set icons. HICON hIcon = (HICON)::LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDR_MAINFRAME), IMAGE_ICON,::GetSystemMetrics(SM_CXICON),::GetSystemMetrics(SM_CYICON),LR_DEFAULTCOLOR); SetIcon(hIcon,TRUE); HICON hIconSmall = (HICON)::LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDR_MAINFRAME), IMAGE_ICON,::GetSystemMetrics(SM_CXSMICON),::GetSystemMetrics(SM_CYSMICON),LR_DEFAULTCOLOR); SetIcon(hIconSmall,FALSE); }*/ if (m_bAppMode) { ModifyStyle(0,WS_MINIMIZEBOX | WS_SYSMENU); ModifyStyleEx(0,WS_EX_APPWINDOW); HMENU hSysMenu = GetSystemMenu(FALSE); ::InsertMenu(hSysMenu,0,MF_BYPOSITION,SC_RESTORE,_T("&Restore")); ::InsertMenu(hSysMenu,2,MF_BYPOSITION,SC_MINIMIZE,_T("Mi&nimize")); ::InsertMenu(hSysMenu,3,MF_BYPOSITION | MF_SEPARATOR,0,_T("")); } // Image lists. InitListImageList(); InitToolBarImageList(); // Create tool bar. CreateToolBarCtrl(); // Recorder combo box. m_DeviceCombo = GetDlgItem(IDC_DEVICECOMBO); std::vector::const_iterator it; for (it = g_DeviceManager.devices().begin(); it != g_DeviceManager.devices().end(); it++) { const ckmmc::Device *pDevice = *it; m_DeviceCombo.AddString(NDeviceUtil::GetDeviceName(*pDevice).c_str()); m_DeviceCombo.SetItemData(m_DeviceCombo.GetCount() - 1, reinterpret_cast(pDevice)); } if (m_DeviceCombo.GetCount() == 0) { m_DeviceCombo.AddString(lngGetString(FAILURE_NODEVICES)); m_DeviceCombo.EnableWindow(false); // Disable the OK button. ::EnableWindow(GetDlgItem(IDOK),false); } m_DeviceCombo.SetCurSel(0); // List view. m_ListView = GetDlgItem(IDC_TRACKLIST); m_ListView.SetExtendedListViewStyle(LVS_EX_FULLROWSELECT); m_ListView.SetImageList(m_hListImageList,LVSIL_SMALL); m_ListView.InsertColumn(0,lngGetString(COLUMN_TRACK),LVCFMT_LEFT,45,0); m_ListView.InsertColumn(1,lngGetString(COLUMN_ADDRESS),LVCFMT_RIGHT,70,1); m_ListView.InsertColumn(2,lngGetString(COLUMN_LENGTH),LVCFMT_LEFT,118,2); // Update the list view. BOOL bDymmy; OnDeviceChange(NULL,NULL,NULL,bDymmy); // Translate the window. Translate(); return TRUE; } LRESULT CTracksDlg::OnDeviceChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // MCI_STATUS_MEDIA_PRESENT? bHandled = false; ckmmc::Device *pDevice = reinterpret_cast(m_DeviceCombo.GetItemData( m_DeviceCombo.GetCurSel())); // Empty the list view and disable the toolbar buttons. m_ListView.DeleteAllItems(); m_ToolBar.EnableButton(ID_TRACK_READ,false); m_ToolBar.EnableButton(ID_TRACK_VERIFY,false); m_ToolBar.EnableButton(ID_TRACK_ERASE,false); // Rescan the bus. CWaitDlg WaitDlg; WaitDlg.Create(m_hWnd); WaitDlg.ShowWindow(SW_SHOW); // Initialize device (detect drive letter, open handle, count tracks). WaitDlg.SetMessage(lngGetString(INIT_DEVICECD)); TCHAR szDriveLetter[3]; szDriveLetter[0] = pDevice->address().device_[0]; szDriveLetter[1] = ':'; szDriveLetter[2] = '\0'; // Open the device by specifying the device name. unsigned long ulResult = 0; unsigned long ulDeviceID = 0; unsigned long ulNumTracks = 0; MCI_OPEN_PARMS mciOpenParms; MCI_SET_PARMS mciSetParms; MCI_STATUS_PARMS mciStatusParms; mciOpenParms.lpstrDeviceType = (TCHAR *)MCI_DEVTYPE_CD_AUDIO; mciOpenParms.lpstrElementName = szDriveLetter; ulResult = mciSendCommand(NULL,MCI_OPEN,MCI_OPEN_TYPE | MCI_OPEN_TYPE_ID | MCI_OPEN_ELEMENT,(DWORD_PTR)&mciOpenParms); if (ulResult != 0) { WaitDlg.DestroyWindow(); return 0; } ulDeviceID = mciOpenParms.wDeviceID; // Set the time format to minute/second/frame (MSF) format. mciSetParms.dwTimeFormat = MCI_FORMAT_MSF; ulResult = mciSendCommand(ulDeviceID,MCI_SET,MCI_SET_TIME_FORMAT, (DWORD_PTR)&mciSetParms); if (ulResult != 0) { mciSendCommand(ulDeviceID,MCI_CLOSE,0,NULL); WaitDlg.DestroyWindow(); return 0; } // Get the number of tracks. mciStatusParms.dwItem = MCI_STATUS_NUMBER_OF_TRACKS; ulResult = mciSendCommand(ulDeviceID,MCI_STATUS,MCI_STATUS_ITEM,(DWORD_PTR)&mciStatusParms); if (ulResult != 0) { mciSendCommand(ulDeviceID,MCI_CLOSE,0,NULL); WaitDlg.DestroyWindow(); return 0; } ulNumTracks = (unsigned long)mciStatusParms.dwReturn; // Track information. TCHAR szBuffer[128]; unsigned int uiListItemCount = 0; for (unsigned long i = 1; i <= ulNumTracks; i++) { mciStatusParms.dwTrack = i; mciStatusParms.dwItem = MCI_CDA_STATUS_TYPE_TRACK; ulResult = mciSendCommand(ulDeviceID,MCI_STATUS,MCI_STATUS_ITEM | MCI_TRACK,(DWORD_PTR)&mciStatusParms); if (ulResult != 0) { mciSendCommand(ulDeviceID,MCI_CLOSE,0,NULL); WaitDlg.DestroyWindow(); return 0; } // Add the new list item. lsprintf(szBuffer,_T("%d"),i); m_ListView.AddItem(uiListItemCount,0,szBuffer,mciStatusParms.dwReturn == MCI_CDA_TRACK_AUDIO); // Wait dialog message. lsnprintf_s(szBuffer,128,lngGetString(INIT_TRACK),i); WaitDlg.SetMessage(szBuffer); // Track position. mciStatusParms.dwItem = MCI_STATUS_POSITION; ulResult = mciSendCommand(ulDeviceID,MCI_STATUS,MCI_STATUS_ITEM | MCI_TRACK,(DWORD_PTR)&mciStatusParms); if (ulResult != 0) { mciSendCommand(ulDeviceID,MCI_CLOSE,0,NULL); WaitDlg.DestroyWindow(); return 0; } lsprintf(szBuffer,_T("%d"),MSFToLBA( MCI_MSF_MINUTE(mciStatusParms.dwReturn), MCI_MSF_SECOND(mciStatusParms.dwReturn), MCI_MSF_FRAME(mciStatusParms.dwReturn))); m_ListView.AddItem(uiListItemCount,1,szBuffer); // Track length. mciStatusParms.dwItem = MCI_STATUS_LENGTH; ulResult = mciSendCommand(ulDeviceID,MCI_STATUS,MCI_STATUS_ITEM | MCI_TRACK,(DWORD_PTR)&mciStatusParms); if (ulResult != 0) { mciSendCommand(ulDeviceID,MCI_CLOSE,0,NULL); WaitDlg.DestroyWindow(); return 0; } unsigned long ulMin = MCI_MSF_MINUTE(mciStatusParms.dwReturn); unsigned long ulSec = MCI_MSF_SECOND(mciStatusParms.dwReturn); unsigned long ulFrame = MCI_MSF_FRAME(mciStatusParms.dwReturn); unsigned long ulSecLen = MSFToLBA(ulMin,ulSec,ulFrame); lsprintf(szBuffer,_T("%02d:%02d:%02d (%d)"), ulMin,ulSec,ulFrame,ulSecLen); m_ListView.AddItem(uiListItemCount,2,szBuffer); // Set the item data to the length of the track (in sectors). m_ListView.SetItemData(uiListItemCount,ulSecLen); uiListItemCount++; } mciSendCommand(ulDeviceID,MCI_CLOSE,0,NULL); WaitDlg.DestroyWindow(); return 0; } bool CTracksDlg::IsDataTrack(int iTrackIndex) { LVITEM lvItem; memset(&lvItem,0,sizeof(LVITEM)); lvItem.iItem = iTrackIndex; lvItem.iSubItem = 0; lvItem.mask = LVIF_IMAGE; m_ListView.GetItem(&lvItem); return lvItem.iImage == 0; } unsigned long CTracksDlg::GetTrackAddress(int iTrackIndex) { TCHAR szTextBuffer[32]; LVITEM lvItem; memset(&lvItem,0,sizeof(LVITEM)); lvItem.iItem = iTrackIndex; lvItem.iSubItem = 1; lvItem.pszText = szTextBuffer; lvItem.cchTextMax = 32; lvItem.mask = LVIF_TEXT; m_ListView.GetItem(&lvItem); return _wtoi(szTextBuffer); } bool CTracksDlg::EncodeTrack(const TCHAR *szFileName,CCodec *pEncoder) { // Find which codec that can be uses for decoding the source file. CCodec *pDecoder = NULL; // Source file information. int iNumChannels = -1; int iSampleRate = -1; int iBitRate = -1; unsigned __int64 uiDuration = 0; for (unsigned int i = 0; i < g_CodecManager.m_Codecs.size(); i++) { // We're only interested in decoders. if ((g_CodecManager.m_Codecs[i]->irc_capabilities() & IRC_HAS_DECODER) == 0) continue; if (g_CodecManager.m_Codecs[i]->irc_decode_init(szFileName,iNumChannels, iSampleRate,iBitRate,uiDuration)) { pDecoder = g_CodecManager.m_Codecs[i]; break; } } if (pDecoder == NULL) { TCHAR szNameBuffer[MAX_PATH]; lstrcpy(szNameBuffer,szFileName); ExtractFileName(szNameBuffer); g_pProgressDlg->notify(ckcore::Progress::ckERROR, lngGetString(ERROR_NODECODER),szNameBuffer); return false; } // Setup the encoder. TCHAR szTargetFile[MAX_PATH]; lstrcpy(szTargetFile,szFileName); ChangeFileExt(szTargetFile,pEncoder->irc_string(IRC_STR_FILEEXT)); // Initialize the encoder. if (!pEncoder->irc_encode_init(szTargetFile,iNumChannels,iSampleRate,iBitRate)) { g_pProgressDlg->notify(ckcore::Progress::ckERROR,lngGetString(ERROR_CODECINIT), pEncoder->irc_string(IRC_STR_ENCODER), iNumChannels,iSampleRate,iBitRate,uiDuration); pDecoder->irc_decode_exit(); return false; } // Encode/decode-process. __int64 iBytesRead = 0; unsigned __int64 uiCurrentTime = 0; #define ENCODE_BUFFER_FACTOR 1024 // Allocate buffer memory. unsigned int uiBufferSize = iNumChannels * ((iBitRate / iSampleRate) >> 3) * ENCODE_BUFFER_FACTOR; unsigned char *pBuffer = new unsigned char[uiBufferSize]; while (true) { iBytesRead = pDecoder->irc_decode_process(pBuffer,uiBufferSize,uiCurrentTime); if (iBytesRead <= 0) break; if (pEncoder->irc_encode_process(pBuffer,iBytesRead) < 0) { g_pProgressDlg->notify(ckcore::Progress::ckERROR,lngGetString(ERROR_ENCODEDATA)); break; } // Update the progres bar. unsigned char ucPercent = (unsigned char)(((double)uiCurrentTime/uiDuration) * 100); g_pProgressDlg->set_progress(ucPercent); } // Free buffer memory. delete [] pBuffer; // Flush. pEncoder->irc_encode_flush(); g_pProgressDlg->set_progress(100); // Destroy the codecs. pEncoder->irc_encode_exit(); pDecoder->irc_decode_exit(); ExtractFileName(szTargetFile); g_pProgressDlg->notify(ckcore::Progress::ckINFORMATION, lngGetString(SUCCESS_ENCODETRACK),szTargetFile); return true; } unsigned long WINAPI CTracksDlg::ReadTrackThread(LPVOID lpThreadParameter) { CTracksDlg *pTracksDlg = (CTracksDlg *)lpThreadParameter; ckmmc::Device *pDevice = reinterpret_cast(pTracksDlg->m_DeviceCombo.GetItemData( pTracksDlg->m_DeviceCombo.GetCurSel())); // Get the selected tracks. TCHAR szTextBuffer[32]; bool bData; unsigned long ulAddress; unsigned long ulLength; unsigned int uiSelCount = pTracksDlg->m_ListView.GetSelectedCount(); unsigned int uiCurTrack = 1; int iItemIndex = -1; iItemIndex = pTracksDlg->m_ListView.GetNextItem(iItemIndex,LVNI_SELECTED); // Holds the full track name. TCHAR szFilePath[MAX_PATH]; while (iItemIndex != -1) { // Get the track type. bData = pTracksDlg->IsDataTrack(iItemIndex); // File path. if (bData) lsprintf(szTextBuffer,_T("Track %d.iso"),iItemIndex + 1); else lsprintf(szTextBuffer,_T("Track %d.wav"),iItemIndex + 1); lstrcpy(szFilePath,pTracksDlg->m_szFolderPath); lstrcat(szFilePath,_T("\\")); lstrcat(szFilePath,szTextBuffer); // Get the track address. ulAddress = pTracksDlg->GetTrackAddress(iItemIndex); // Get the track length. ulLength = (unsigned long)pTracksDlg->m_ListView.GetItemData(iItemIndex); // Check if we're on the last track. We need to know when to finish the progress window. if (uiCurTrack == uiSelCount) { if (bData) { bool bResult = g_Core2.ReadDataTrack(*pDevice,g_pProgressDlg, static_cast(iItemIndex + 1), true,szFilePath); g_pProgressDlg->set_progress(100); g_pProgressDlg->NotifyCompleted(); if (bResult) { g_pProgressDlg->set_status(lngGetString(PROGRESS_DONE)); } else { g_pProgressDlg->set_status(lngGetString(PROGRESS_FAILED)); ckcore::File::remove(szFilePath); return 0; } } else { if (pTracksDlg->m_pEncoder != NULL) { if (g_Core.ReadAudioTrackEx(*pDevice,g_pProgressDlg,szFilePath,iItemIndex + 1) != BURNRESULT_OK) { ckcore::File::remove(szFilePath); return 0; } // Encode. TCHAR szStatus[256]; lsnprintf_s(szStatus,256,lngGetString(PROGRESS_ENCODETRACK), pTracksDlg->m_pEncoder->irc_string(IRC_STR_ENCODER)); g_pProgressDlg->set_status(szStatus); if (EncodeTrack(szFilePath,pTracksDlg->m_pEncoder)) ckcore::File::remove(szFilePath); g_pProgressDlg->set_status(lngGetString(PROGRESS_DONE)); g_pProgressDlg->NotifyCompleted(); } else { if (!g_Core.ReadAudioTrack(*pDevice,g_pProgressDlg,szFilePath,iItemIndex + 1)) { ckcore::File::remove(szFilePath); return 0; } } } } else { if (bData) { if (g_Core2.ReadDataTrack(*pDevice,g_pProgressDlg,static_cast(iItemIndex + 1), true,szFilePath)) { g_pProgressDlg->set_progress(0); } else { ckcore::File::remove(szFilePath); g_pProgressDlg->set_progress(100); g_pProgressDlg->set_status(lngGetString(PROGRESS_FAILED)); g_pProgressDlg->NotifyCompleted(); return 0; } } else { if (g_Core.ReadAudioTrackEx(*pDevice,g_pProgressDlg,szFilePath,iItemIndex + 1) != BURNRESULT_OK) { ckcore::File::remove(szFilePath); return 0; } // Encode audio. if (pTracksDlg->m_pEncoder != NULL) { TCHAR szStatus[256]; lsnprintf_s(szStatus,256,lngGetString(PROGRESS_ENCODETRACK), pTracksDlg->m_pEncoder->irc_string(IRC_STR_ENCODER)); g_pProgressDlg->set_status(szStatus); if (EncodeTrack(szFilePath,pTracksDlg->m_pEncoder)) ckcore::File::remove(szFilePath); } // Check if the encoding has been canceled. if (g_pProgressDlg->cancelled()) { g_pProgressDlg->NotifyCompleted(); return 0; } } } uiCurTrack++; iItemIndex = pTracksDlg->m_ListView.GetNextItem(iItemIndex,LVNI_SELECTED); } return 0; } unsigned long WINAPI CTracksDlg::ScanTrackThread(LPVOID lpThreadParameter) { CTracksDlg *pTracksDlg = (CTracksDlg *)lpThreadParameter; ckmmc::Device *pDevice = reinterpret_cast(pTracksDlg->m_DeviceCombo.GetItemData( pTracksDlg->m_DeviceCombo.GetCurSel())); // Get the selected tracks. unsigned long ulAddress; unsigned long ulLength; unsigned int uiSelCount = pTracksDlg->m_ListView.GetSelectedCount(); unsigned int uiCurTrack = 1; int iItemIndex = -1; iItemIndex = pTracksDlg->m_ListView.GetNextItem(iItemIndex,LVNI_SELECTED); while (iItemIndex != -1) { // Get the track address. ulAddress = pTracksDlg->GetTrackAddress(iItemIndex); // Get the track length. ulLength = (unsigned long)pTracksDlg->m_ListView.GetItemData(iItemIndex); // Check if we're on the last track. We need to know when to finish the progress window. if (uiCurTrack == uiSelCount) { if (!g_Core.ScanTrack(*pDevice,g_pProgressDlg,iItemIndex + 1, ulAddress,ulAddress + ulLength)) { return 0; } } else { if (g_Core.ScanTrackEx(*pDevice,g_pProgressDlg,iItemIndex + 1, ulAddress,ulAddress + ulLength) != BURNRESULT_OK) { return 0; } } uiCurTrack++; iItemIndex = pTracksDlg->m_ListView.GetNextItem(iItemIndex,LVNI_SELECTED); } return 0; } LRESULT CTracksDlg::OnReadTrack(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CSaveTracksDlg SaveTracksDlg; if (SaveTracksDlg.DoModal() == IDOK) { ckmmc::Device *pDevice = reinterpret_cast(m_DeviceCombo.GetItemData( m_DeviceCombo.GetCurSel())); // Disable the main frame. EnableWindow(false); // Create and display the progress dialog. if (!g_pProgressDlg->IsWindow()) g_pProgressDlg->Create(m_hWnd); g_pProgressDlg->ShowWindow(true); g_pProgressDlg->SetWindowText(lngGetString(STITLE_READTRACK)); g_pProgressDlg->Reset(); g_pProgressDlg->AttachProcess(&g_Core); g_pProgressDlg->AttachHost(m_hWnd); ProcessMessages(); // Set the device information. g_pProgressDlg->SetDevice(*pDevice); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); lstrcpy(m_szFolderPath,g_SaveTracksSettings.m_szTarget); m_pEncoder = SaveTracksDlg.GetEncoder(); // Create the new thread. unsigned long ulThreadID = 0; HANDLE hThread = ::CreateThread(NULL,0,ReadTrackThread,this,0,&ulThreadID); ::CloseHandle(hThread); } bHandled = false; return 0; } LRESULT CTracksDlg::OnVerifyTrack(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { ckmmc::Device *pDevice = reinterpret_cast(m_DeviceCombo.GetItemData( m_DeviceCombo.GetCurSel())); // Disable the main frame. EnableWindow(false); // Create and display the progress dialog. if (!g_pProgressDlg->IsWindow()) g_pProgressDlg->Create(m_hWnd); g_pProgressDlg->ShowWindow(true); g_pProgressDlg->SetWindowText(lngGetString(STITLE_SCANTRACK)); g_pProgressDlg->Reset(); g_pProgressDlg->AttachProcess(&g_Core); g_pProgressDlg->AttachHost(m_hWnd); ProcessMessages(); // Set the device information. g_pProgressDlg->SetDevice(*pDevice); g_pProgressDlg->set_status(lngGetString(PROGRESS_INIT)); // Create the new thread. unsigned long ulThreadID = 0; HANDLE hThread = ::CreateThread(NULL,0,ScanTrackThread,this,0,&ulThreadID); ::CloseHandle(hThread); bHandled = false; return 0; } LRESULT CTracksDlg::OnEraseTrack(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { MessageBox(_T("Not yet implemented."),_T("Information"),MB_OK | MB_ICONINFORMATION); bHandled = false; return 0; } LRESULT CTracksDlg::OnToolBarGetInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { bHandled = true; // The string ID is the same as the button ID. LPTOOLTIPTEXT pTipText = (LPTOOLTIPTEXT)pNMH; // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a hint translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("hint"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr((unsigned long)pTipText->hdr.idFrom,szStrValue)) { pTipText->lpszText = szStrValue; return 0; } } } pTipText->lpszText = MAKEINTRESOURCE(pTipText->hdr.idFrom); return 0; } LRESULT CTracksDlg::OnListItemChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { if (m_ListView.GetSelectedCount() > 0) { m_ToolBar.EnableButton(ID_TRACK_READ,true); m_ToolBar.EnableButton(ID_TRACK_VERIFY,true); m_ToolBar.EnableButton(ID_TRACK_ERASE,true); } else { m_ToolBar.EnableButton(ID_TRACK_READ,false); m_ToolBar.EnableButton(ID_TRACK_VERIFY,false); m_ToolBar.EnableButton(ID_TRACK_ERASE,false); } bHandled = false; return 0; } LRESULT CTracksDlg::OnListKeyDown(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { LPNMLVKEYDOWN KeyDown = (LPNMLVKEYDOWN)pNMH; // Ctrl+A = select all if (KeyDown->wVKey == _T('A') && (GetKeyState(VK_CONTROL) & 0x8000)) { const int iItemCount = m_ListView.GetItemCount(); for (int i = 0; i < iItemCount; ++i ) { ATLVERIFY(TRUE == m_ListView.SetItemState(i,LVIS_SELECTED,LVIS_SELECTED)); } bHandled = TRUE; } else { bHandled = FALSE; } return 0; } LRESULT CTracksDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { EndDialog(wID); return FALSE; } LRESULT CTracksDlg::OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { TCHAR szFileName[MAX_PATH]; GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,lngGetManual()); lstrcat(szFileName,_T("::/how_to_use/manage_tracks.html")); HtmlHelp(m_hWnd,szFileName,HH_DISPLAY_TOC,NULL); return 0; } ================================================ FILE: src/app/dialog/tracks_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #include "infrarecorder.hh" class CTracksDlg : public CDialogImpl { private: bool m_bAppMode; HIMAGELIST m_hListImageList; HIMAGELIST m_hToolBarImageList; CComboBox m_DeviceCombo; CListViewCtrl m_ListView; CToolBarCtrl m_ToolBar; // Needed to make the thread access what target folder that where selected. TCHAR m_szFolderPath[MAX_PATH]; CCodec *m_pEncoder; static bool EncodeTrack(const TCHAR *szFileName,CCodec *pEncoder); static unsigned long WINAPI ReadTrackThread(LPVOID lpThreadParameter); static unsigned long WINAPI ScanTrackThread(LPVOID lpThreadParameter); unsigned long MSFToLBA(unsigned long ulMin,unsigned long ulSec,unsigned long ulFrame); bool Translate(); void InitListImageList(); void InitToolBarImageList(); void AddToolBarSeparator(); void AddToolBarButton(int iCommand,int iBitmap); void CreateToolBarCtrl(); bool IsDataTrack(int iTrackIndex); unsigned long GetTrackAddress(int iTrackIndex); public: enum { IDD = IDD_TRACKSDLG }; CTracksDlg(bool bAppMode); ~CTracksDlg(); private: BEGIN_MSG_MAP(CTracksDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_HANDLER(IDC_DEVICECOMBO,CBN_SELCHANGE,OnDeviceChange) COMMAND_ID_HANDLER(ID_TRACK_READ,OnReadTrack) COMMAND_ID_HANDLER(ID_TRACK_VERIFY,OnVerifyTrack) COMMAND_ID_HANDLER(ID_TRACK_ERASE,OnEraseTrack) NOTIFY_CODE_HANDLER(TTN_GETDISPINFO,OnToolBarGetInfo) NOTIFY_HANDLER(IDC_TRACKLIST,LVN_ITEMCHANGED,OnListItemChanged) NOTIFY_HANDLER(IDC_TRACKLIST,LVN_KEYDOWN,OnListKeyDown) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnOK) COMMAND_HANDLER(IDC_HELPBUTTON,BN_CLICKED,OnHelp) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnDeviceChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnReadTrack(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnVerifyTrack(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnEraseTrack(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnToolBarGetInfo(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnListItemChanged(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnListKeyDown(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnHelp(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/dialog/wait_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "wait_dlg.hh" CWaitDlg::CWaitDlg() { } CWaitDlg::~CWaitDlg() { } void CWaitDlg::SetMessage(const TCHAR *szMessage) { SetDlgItemText(IDC_INFOSTATIC,szMessage); } LRESULT CWaitDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { CenterWindow(GetParent()); return TRUE; } LRESULT CWaitDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { return TRUE; } ================================================ FILE: src/app/dialog/wait_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" class CWaitDlg : public CDialogImpl { public: enum { IDD = IDD_WAITDLG }; CWaitDlg(); ~CWaitDlg(); void SetMessage(const TCHAR *szMessage); BEGIN_MSG_MAP(CWaitDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/app/directory_monitor.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "directory_monitor.hh" CDirectoryMonitor::CDirectoryMonitor() { } CDirectoryMonitor::~CDirectoryMonitor() { } /* CDirectoryMonitor::Register --------------------------- Register the change notify entry using SHChangeNotifyEntry. The hWndNotify handle should be the window to receive the messages. uiMsg the notification number. It returns true of no errors occured, false otherwise. */ bool CDirectoryMonitor::Register(HWND hWndNotify,unsigned int uiMsg,int iFilter, LPITEMIDLIST pidl,bool bRecursive) { SHChangeNotifyEntry shNotifyEntry = { pidl,bRecursive }; /* Where are these defined? SHCNRF_InterruptLevel = 0x0001 SHCNRF_ShellLevel = 0x0002 SHCNRF_RecursiveInterrupt = 0x1000 SHCNRF_NewDelivery = 0x8000 */ int iFlags = 0x0003; // SHCNRF_InterruptLevel & SHCNRF_ShellLevel if (bRecursive) iFlags |= 0x1000; m_ulNotifyID = SHChangeNotifyRegister(hWndNotify,iFlags,iFilter,uiMsg,1,&shNotifyEntry); if (!m_ulNotifyID) return false; return true; } bool CDirectoryMonitor::Deregister() { if (!m_ulNotifyID) return false; if (SUCCEEDED(SHChangeNotifyDeregister(m_ulNotifyID))) return true; return false; } ================================================ FILE: src/app/directory_monitor.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CDirectoryMonitor { private: unsigned long m_ulNotifyID; public: CDirectoryMonitor(); ~CDirectoryMonitor(); bool Register(HWND hWndNotify,unsigned int uiMsg,int iFilter,LPITEMIDLIST pidl, bool bRecursive); bool Deregister(); }; ================================================ FILE: src/app/effects.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "effects.hh" ================================================ FILE: src/app/effects.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once // Configuration. #define EFFECTWINDOW_HEIGHT 256 #define EFFECTWINDOW_OVERLAP 25 // Messages. #define WM_CKEFFECTS_INITIALIZED WM_APP + 0 #define WM_CKEFFECTS_DESTROY WM_APP + 1 #define WM_CKEFFECTS_STARTSMOKE WM_APP + 2 #define WM_CKEFFECTS_STOPSMOKE WM_APP + 3 #define WM_CKEFFECTS_KILLSMOKE WM_APP + 4 #define SMOKE_INIT\ m_hWndEffects = NULL; #define SMOKE_START\ if (m_hWndEffects == NULL)\ {\ if (g_WinVer.m_ulMajorVersion == MAJOR_WINVISTA &&\ g_WinVer.m_ulMinorVersion == MINOR_WINVISTA &&\ g_GlobalSettings.m_bSmoke)\ {\ bool bHasDependencies = false;\ HINSTANCE hDummy = LoadLibrary(_T("d3d8thk.dll"));\ if (hDummy)\ {\ FreeLibrary(hDummy);\ hDummy = LoadLibrary(_T("d3d9.dll"));\ if (hDummy)\ {\ FreeLibrary(hDummy);\ hDummy = LoadLibrary(_T("d3dx9_32.dll"));\ if (hDummy)\ {\ FreeLibrary(hDummy);\ hDummy = LoadLibrary(_T("dwmapi.dll"));\ if (hDummy)\ {\ FreeLibrary(hDummy);\ bHasDependencies = true;\ }\ }\ }\ }\ if (bHasDependencies)\ {\ RECT rcWindow;\ GetWindowRect(&rcWindow);\ TCHAR szParam[128];\ lsprintf(szParam,_T("-host=%I64x -dim=%d,%d,%d,%d"),(__int64)m_hWnd,rcWindow.left,\ rcWindow.top - EFFECTWINDOW_HEIGHT + EFFECTWINDOW_OVERLAP,\ rcWindow.right - rcWindow.left,EFFECTWINDOW_HEIGHT);\ TCHAR szFileName[MAX_PATH];\ GetModuleFileName(NULL,szFileName,MAX_PATH - 1);\ ExtractFilePath(szFileName);\ IncludeTrailingBackslash(szFileName);\ lstrcat(szFileName,_T("smoke.exe"));\ ShellExecute(HWND_DESKTOP,_T("open"),szFileName,szParam,NULL,SW_SHOWDEFAULT);\ }\ }\ } #define SMOKE_STOP\ if (m_hWndEffects != NULL)\ {\ ::PostMessage(m_hWndEffects,WM_CKEFFECTS_DESTROY,NULL,NULL);\ m_hWndEffects = NULL;\ } #define SMOKE_EVENTS\ MESSAGE_HANDLER(WM_WINDOWPOSCHANGED,OnWindowPosChanged)\ MESSAGE_HANDLER(WM_SIZE,OnSize)\ MESSAGE_HANDLER(WM_ACTIVATEAPP,OnActivateApp)\ MESSAGE_HANDLER(WM_CKEFFECTS_INITIALIZED,OnEffectInitialized) #define SMOKE_IMPL\ LRESULT OnWindowPosChanged(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled)\ {\ WINDOWPOS *pWindowPos = (WINDOWPOS *)lParam;\ if (m_hWndEffects != NULL)\ {\ RECT rcWindow;\ ::GetWindowRect(m_hWndEffects,&rcWindow);\ ::MoveWindow(m_hWndEffects,pWindowPos->x,pWindowPos->y - EFFECTWINDOW_HEIGHT + EFFECTWINDOW_OVERLAP,rcWindow.right - rcWindow.left,\ rcWindow.bottom - rcWindow.top,TRUE);\ }\ bHandled = false;\ return TRUE;\ }\ LRESULT OnSize(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled)\ {\ switch (wParam)\ {\ case SIZE_MINIMIZED:\ ::PostMessage(m_hWndEffects,WM_CKEFFECTS_KILLSMOKE,NULL,NULL);\ break;\ case SIZE_RESTORED:\ ::PostMessage(m_hWndEffects,WM_CKEFFECTS_STARTSMOKE,NULL,NULL);\ break;\ }\ bHandled = false;\ return TRUE;\ }\ LRESULT OnActivateApp(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled)\ {\ if (m_hWndEffects)\ {\ ::SetWindowPos(m_hWndEffects,m_hWnd,0,0,0,0,\ SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE | SWP_NOREDRAW | SWP_ASYNCWINDOWPOS);\ }\ bHandled = false;\ return TRUE;\ }\ LRESULT OnEffectInitialized(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled)\ {\ m_hWndEffects = (HWND)lParam;\ ::PostMessage(m_hWndEffects,WM_CKEFFECTS_STARTSMOKE,NULL,NULL);\ return TRUE;\ }\ private:\ HWND m_hWndEffects;\ public: ================================================ FILE: src/app/enum_fmt_etc.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "enum_fmt_etc.hh" HRESULT CreateEnumFmtEtc(unsigned int uiNumFormats,FORMATETC *pFormats, IEnumFORMATETC **ppEnumFormatEtc) { if (uiNumFormats == 0 || pFormats == NULL || ppEnumFormatEtc == NULL) return E_INVALIDARG; *ppEnumFormatEtc = new CEnumFmtEtc(pFormats,uiNumFormats); return (*ppEnumFormatEtc) ? S_OK : E_OUTOFMEMORY; } CEnumFmtEtc::CEnumFmtEtc(FORMATETC *pFormats,unsigned int uiNumFormats) { m_lRefCount = 1; m_uiFormatIndex = 0; m_uiNumFormats = uiNumFormats; m_pFormats = new FORMATETC[uiNumFormats]; for (unsigned int i = 0; i < uiNumFormats; i++) { memcpy(&m_pFormats[i],&pFormats[i],sizeof(FORMATETC)); if (pFormats->ptd) { m_pFormats[i].ptd = (DVTARGETDEVICE *)CoTaskMemAlloc(sizeof(DVTARGETDEVICE)); memcpy(&m_pFormats[i].ptd,&pFormats[i].ptd,sizeof(DVTARGETDEVICE)); } } } CEnumFmtEtc::~CEnumFmtEtc() { if (m_pFormats) { for (unsigned int i = 0; i < m_uiNumFormats; i++) { if (m_pFormats[i].ptd) CoTaskMemFree(m_pFormats[i].ptd); } delete [] m_pFormats; } } void CEnumFmtEtc::SetIndex(unsigned int uiFormatIndex) { m_uiFormatIndex = uiFormatIndex; } ULONG __stdcall CEnumFmtEtc::AddRef() { // Increment object reference count. return InterlockedIncrement(&m_lRefCount); } ULONG __stdcall CEnumFmtEtc::Release() { // Decrement object reference count. LONG lCount = InterlockedDecrement(&m_lRefCount); if (lCount == 0) { delete this; return 0; } else { return lCount; } } HRESULT __stdcall CEnumFmtEtc::QueryInterface(REFIID iid,void **ppvObject) { // Check to see what interface has been requested. if (iid == IID_IEnumFORMATETC || iid == IID_IUnknown) { AddRef(); *ppvObject = this; return S_OK; } else { *ppvObject = 0; return E_NOINTERFACE; } } HRESULT __stdcall CEnumFmtEtc::Next(ULONG celt,FORMATETC *pFormatEtc,ULONG *pceltFetched) { unsigned int uiCopied = 0; if (celt == 0 || pFormatEtc == 0) return E_INVALIDARG; while (m_uiFormatIndex < m_uiNumFormats && uiCopied < celt) { // Copy the format data. memcpy(&pFormatEtc[uiCopied],&m_pFormats[m_uiFormatIndex],sizeof(FORMATETC)); if (m_pFormats[m_uiFormatIndex].ptd) { pFormatEtc[uiCopied].ptd = (DVTARGETDEVICE *)CoTaskMemAlloc(sizeof(DVTARGETDEVICE)); memcpy(&pFormatEtc[uiCopied].ptd,&m_pFormats[m_uiFormatIndex].ptd,sizeof(DVTARGETDEVICE)); } uiCopied++; m_uiFormatIndex++; } if (pceltFetched != 0) *pceltFetched = uiCopied; // Was all requested data copied? return (uiCopied == celt) ? S_OK : S_FALSE; } HRESULT __stdcall CEnumFmtEtc::Skip(ULONG celt) { m_uiFormatIndex += celt; return (m_uiFormatIndex <= m_uiNumFormats) ? S_OK : S_FALSE; } HRESULT __stdcall CEnumFmtEtc::Reset() { m_uiFormatIndex = 0; return S_OK; } HRESULT __stdcall CEnumFmtEtc::Clone(IEnumFORMATETC **ppEnumFormatEtc) { HRESULT hResult; // Make a duplicate enumerator. hResult = CreateEnumFmtEtc(m_uiNumFormats,m_pFormats,ppEnumFormatEtc); if (hResult == S_OK) ((CEnumFmtEtc *)*ppEnumFormatEtc)->SetIndex(m_uiFormatIndex); return hResult; } ================================================ FILE: src/app/enum_fmt_etc.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CEnumFmtEtc : public IEnumFORMATETC { private: long m_lRefCount; unsigned int m_uiNumFormats; unsigned int m_uiFormatIndex; FORMATETC *m_pFormats; public: CEnumFmtEtc(FORMATETC *pFormats,unsigned int uiNumFormats); ~CEnumFmtEtc(); void SetIndex(unsigned int uiFormatIndex); // IUnknown members. HRESULT __stdcall QueryInterface(REFIID iid,void **ppvObject); ULONG __stdcall AddRef(); ULONG __stdcall Release(); // IEnumFormatEtc members. HRESULT __stdcall Next(ULONG celt,FORMATETC *rgelt,ULONG *pceltFetched); HRESULT __stdcall Skip(ULONG celt); HRESULT __stdcall Reset(); HRESULT __stdcall Clone(IEnumFORMATETC **ppEnumFormatEtc); }; HRESULT CreateEnumFmtEtc(unsigned int uiNumFormats,FORMATETC *pFormats, IEnumFORMATETC **ppEnumFormatEtc); ================================================ FILE: src/app/files_data_object.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "files_data_object.hh" #include "enum_fmt_etc.hh" CFilesDataObject::CFilesDataObject() { // Reference count must ALWAYS start at 1. m_lRefCount = 1; memset(&m_FormatEtc,0,sizeof(m_FormatEtc)); m_FormatEtc.cfFormat = CF_HDROP; m_FormatEtc.dwAspect = DVASPECT_CONTENT; m_FormatEtc.lindex = 0; m_FormatEtc.ptd = NULL; m_FormatEtc.tymed = TYMED_HGLOBAL; memset(&m_StgMedium,0,sizeof(m_StgMedium)); m_StgMedium.tymed = TYMED_HGLOBAL; } CFilesDataObject::~CFilesDataObject() { ReleaseStgMedium(&m_StgMedium); } bool CFilesDataObject::IsFormatSupported(FORMATETC *pFormatEtc) { if (m_FormatEtc.cfFormat == pFormatEtc->cfFormat && m_FormatEtc.dwAspect == pFormatEtc->dwAspect && m_FormatEtc.tymed & pFormatEtc->tymed) { return true; } return false; } void CFilesDataObject::Reset() { m_Files.clear(); } void CFilesDataObject::AddFile(const TCHAR *szFileName) { m_Files.push_back(szFileName); } HRESULT __stdcall CFilesDataObject::QueryInterface(REFIID iid,void **ppvObject) { // Check to see what interface has been requested. if (iid == IID_IDataObject || iid == IID_IUnknown) { AddRef(); *ppvObject = this; return S_OK; } else { *ppvObject = 0; return E_NOINTERFACE; } } ULONG __stdcall CFilesDataObject::AddRef() { // Increment object reference count. return InterlockedIncrement(&m_lRefCount); } ULONG __stdcall CFilesDataObject::Release() { // Decrement object reference count. LONG lCount = InterlockedDecrement(&m_lRefCount); if (lCount == 0) { delete this; return 0; } else { return lCount; } } HRESULT __stdcall CFilesDataObject::GetData(FORMATETC *pFormatEtc,STGMEDIUM *pStgMedium) { if (!IsFormatSupported(pFormatEtc)) return DV_E_FORMATETC; // Calculate the memory needed for the file names. size_t iTotalNameLength = 0; std::vector::const_iterator itFile; for (itFile = m_Files.begin(); itFile != m_Files.end(); itFile++) iTotalNameLength += (unsigned int)(*itFile).length() + 1; // Copy the file name data into global memory buffer. pStgMedium->tymed = m_StgMedium.tymed; pStgMedium->pUnkForRelease = 0; pStgMedium->hGlobal = GlobalAlloc(GMEM_SHARE,sizeof(DROPFILES) + (iTotalNameLength + 1) * sizeof(TCHAR)); DROPFILES *pDropFiles = (DROPFILES *)GlobalLock(pStgMedium->hGlobal); pDropFiles->pFiles = sizeof(DROPFILES); pDropFiles->fWide = TRUE; TCHAR *szFiles = (TCHAR *)((unsigned char *)pDropFiles + sizeof(DROPFILES)); size_t iPos = 0; // Copy the file names into the global memory. for (itFile = m_Files.begin(); itFile != m_Files.end(); itFile++) { size_t iPathLength = (*itFile).length(); memcpy(szFiles + iPos,(*itFile).c_str(),iPathLength * sizeof(TCHAR) + sizeof(TCHAR)); iPos += iPathLength + 1; } szFiles[iTotalNameLength] = '\0'; GlobalUnlock(pDropFiles); return S_OK; } HRESULT CFilesDataObject::GetDataHere(FORMATETC *pFormatEtc,STGMEDIUM *pMedium) { return DATA_E_FORMATETC; } HRESULT __stdcall CFilesDataObject::QueryGetData(FORMATETC *pFormatEtc) { return IsFormatSupported(pFormatEtc) ? S_OK : DV_E_FORMATETC; } HRESULT CFilesDataObject::GetCanonicalFormatEtc(FORMATETC *pFormatEct,FORMATETC *pFormatEtcOut) { // MUST be set to NULL. pFormatEtcOut->ptd = NULL; return E_NOTIMPL; } HRESULT __stdcall CFilesDataObject::SetData(FORMATETC *pFormatEtc,STGMEDIUM *pMedium,BOOL fRelease) { return E_NOTIMPL; } HRESULT __stdcall CFilesDataObject::EnumFormatEtc(DWORD dwDirection,IEnumFORMATETC **ppEnumFormatEtc) { if (dwDirection == DATADIR_GET) { // Windows 2000 and newer only. //return SHCreateStdEnumFmtEtc(1,&m_FormatEtc,ppEnumFormatEtc); return CreateEnumFmtEtc(1,&m_FormatEtc,ppEnumFormatEtc); } else { return E_NOTIMPL; } } HRESULT CFilesDataObject::DAdvise(FORMATETC *pFormatEtc,DWORD advf,IAdviseSink *pAdvSink, DWORD *pdwConnection) { return OLE_E_ADVISENOTSUPPORTED; } HRESULT CFilesDataObject::DUnadvise(DWORD dwConnection) { return OLE_E_ADVISENOTSUPPORTED; } HRESULT CFilesDataObject::EnumDAdvise(IEnumSTATDATA **ppEnumAdvise) { return OLE_E_ADVISENOTSUPPORTED; } ================================================ FILE: src/app/files_data_object.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include class CFilesDataObject : public IDataObject { private: long m_lRefCount; FORMATETC m_FormatEtc; STGMEDIUM m_StgMedium; std::vector m_Files; bool IsFormatSupported(FORMATETC *pFormatEtc); public: CFilesDataObject(); ~CFilesDataObject(); void Reset(); void AddFile(const TCHAR *szFileName); // IUnknown members. HRESULT __stdcall QueryInterface(REFIID iid,void **ppvObject); ULONG __stdcall AddRef(); ULONG __stdcall Release(); // IDataObject members. HRESULT __stdcall GetData(FORMATETC *pFormatEtc,STGMEDIUM *pmedium); HRESULT __stdcall GetDataHere(FORMATETC *pFormatEtc,STGMEDIUM *pmedium); HRESULT __stdcall QueryGetData(FORMATETC *pFormatEtc); HRESULT __stdcall GetCanonicalFormatEtc(FORMATETC *pFormatEct,FORMATETC *pFormatEtcOut); HRESULT __stdcall SetData(FORMATETC *pFormatEtc,STGMEDIUM *pMedium,BOOL fRelease); HRESULT __stdcall EnumFormatEtc(DWORD dwDirection, IEnumFORMATETC **ppEnumFormatEtc); HRESULT __stdcall DAdvise(FORMATETC *pFormatEtc,DWORD advf,IAdviseSink *,DWORD *); HRESULT __stdcall DUnadvise(DWORD dwConnection); HRESULT __stdcall EnumDAdvise(IEnumSTATDATA **ppEnumAdvise); }; ================================================ FILE: src/app/infrarecorder.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "Resource.h" #include "main_frm.hh" #include #include #include "progress_dlg.hh" #include "simple_progress_dlg.hh" #include "splash_window.hh" #include "log_dlg.hh" #include "settings.hh" #include "settings_manager.hh" #include "string_table.hh" #include "lang_util.hh" #include "action_manager.hh" #include "temp_manager.hh" #include "info_dlg.hh" #include "about_window.hh" #include "infrarecorder.hh" CAppModule _Module; // Global codec manager object. CCodecManager g_CodecManager; // Global device manager object. ckmmc::DeviceManager g_DeviceManager; // Global pointers to GUI objects owned by this file. CLogDlg *g_pLogDlg = NULL; CMainFrame *g_pMainFrame = NULL; CProgressDlg *g_pProgressDlg = NULL; CSimpleProgressDlg *g_pSimpleProgressDlg = NULL; CAboutWindow *g_pAboutWnd = NULL; #ifdef _DEBUG const ckcore::tchar SAVE_ENGLISH_STRINGS_PARAM[] = _T("-englishstrings "); static int SaveEnglishStrings(const TCHAR * const szFileName) { try { const ckcore::tchar BLANKS[] = _T(" \t"); ckcore::tstring FileName(szFileName); TrimStr(FileName,BLANKS); if (FileName.empty()) throw ckcore::Exception2(_T("Missing filename.")); ckcore::File File(FileName.c_str()); if (!File.open(ckcore::File::ckOPEN_WRITE)) throw ckcore::Exception2(_T("Error opening file for writing.")); // Write byte order mark. unsigned short usBOM = BOM_UTF32BE; File.write(&usBOM,2); const ckcore::tchar CRLF[] = ckT("\r\n"); WriteString(File,CRLF); WriteString(File,ckT("[strings]")); WriteString(File,CRLF); for (unsigned i = 0; i < _countof(g_szStringTable); ++i) { const TCHAR * const szEnglishStr = g_szStringTable[i]; if (szEnglishStr[0] == _T('\0')) continue; ckcore::tstring Str = ckcore::string::formatstr(_T("0x%04x=%s%s"),i,szEnglishStr,CRLF); WriteString(File,Str.c_str()); } ATLVERIFY(true == File.close()); } catch (const std::exception &e) { ckcore::rethrow_with_pfx(e,_T("Error processing command-line option %s: "),SAVE_ENGLISH_STRINGS_PARAM); } return 0; } #endif void PerformDeviceScan() { // Launch the splash window by the safe function because splash screens // are not supported on systems older than Windows 2000. CSplashWindow SplashWindow; SplashWindow.SafeCreate(); g_DeviceManager.scan(&SplashWindow); SplashWindow.SafeDestroy(); if (g_DeviceManager.devices().size() == 0) { if (g_GlobalSettings.m_bNoDevWarning) { CInfoDlg InfoDlg(&g_GlobalSettings.m_bNoDevWarning, lngGetString(WARNING_NODEVICES), INFODLG_NOCANCEL | INFODLG_ICONWARNING); InfoDlg.DoModal(); } } } int Run(LPTSTR lpstrCmdLine = NULL,int nCmdShow = SW_SHOWDEFAULT) { CMessageLoop MainLoop; _Module.AddMessageLoop(&MainLoop); if (g_pMainFrame->CreateEx() == NULL) { ATLTRACE(_T("Main window creation failed!\n")); return 0; } // Load the last used window position and size. if (g_DynamicSettings.m_rcWindow.left != -1 && g_DynamicSettings.m_rcWindow.right != -1 && g_DynamicSettings.m_rcWindow.top != -1 && g_DynamicSettings.m_rcWindow.bottom != -1) { if (g_pMainFrame->m_bDefaultWizard) { RECT rcWindow = g_DynamicSettings.m_rcWindow; rcWindow.right = rcWindow.left + 500; rcWindow.bottom = rcWindow.top + 400; g_pMainFrame->SetWindowPos(HWND_TOP,&rcWindow,0); } else { g_pMainFrame->SetWindowPos(HWND_TOP,&g_DynamicSettings.m_rcWindow,0); } } else { if (g_pMainFrame->m_bDefaultWizard) { RECT rcWindow = g_DynamicSettings.m_rcWindow; rcWindow.right = rcWindow.left + 500; rcWindow.bottom = rcWindow.top + 400; g_pMainFrame->SetWindowPos(HWND_TOP,&rcWindow,0); } g_pMainFrame->CenterWindow(); } g_pMainFrame->ShowWindow(g_DynamicSettings.m_bWinMaximized ? SW_SHOWMAXIMIZED : nCmdShow); int nRet = MainLoop.Run(); _Module.RemoveMessageLoop(); return nRet; } INT_PTR ParseAndRun(LPTSTR lpstrCmdLine,int nCmdShow = SW_SHOWDEFAULT) { g_pMainFrame->m_bDefaultWizard = g_GlobalSettings.m_bShowWizard; // FIXME: This is an absolutely horrible parameter parsing implementation. // Default project selection. if (!lstrncmp(lpstrCmdLine,_T("-project="),9)) { lpstrCmdLine += 9; if (!lstrncmp(lpstrCmdLine,_T("data"),4)) { g_pMainFrame->m_iDefaultProjType = PROJECTTYPE_DATA; g_pMainFrame->m_bDefaultWizard = false; lpstrCmdLine += 4; } else if (!lstrncmp(lpstrCmdLine,_T("audio"),5)) { g_pMainFrame->m_iDefaultProjType = PROJECTTYPE_AUDIO; g_pMainFrame->m_bDefaultWizard = false; lpstrCmdLine += 5; } else if (!lstrncmp(lpstrCmdLine,_T("mixed"),5)) { g_pMainFrame->m_iDefaultProjType = PROJECTTYPE_MIXED; g_pMainFrame->m_bDefaultWizard = false; lpstrCmdLine += 5; } else if (!lstrncmp(lpstrCmdLine,_T("dvdvideo"),8)) { g_pMainFrame->m_iDefaultProjType = PROJECTTYPE_DATA; g_pMainFrame->m_iDefaultMedia = SPACEMETER_SIZE_DVD; g_pMainFrame->m_bDefaultProjDVDVideo = true; g_pMainFrame->m_bDefaultWizard = false; lpstrCmdLine += 8; } if (*lpstrCmdLine) lpstrCmdLine++; } // Default media selection. if (!lstrncmp(lpstrCmdLine,_T("-media="),7)) { lpstrCmdLine += 7; if (!lstrcmp(lpstrCmdLine,_T("dldvd"))) g_pMainFrame->m_iDefaultMedia = SPACEMETER_SIZE_DLDVD; else if (!lstrcmp(lpstrCmdLine,_T("dvd"))) g_pMainFrame->m_iDefaultMedia = SPACEMETER_SIZE_DVD; else if (!lstrcmp(lpstrCmdLine,_T("cd"))) g_pMainFrame->m_iDefaultMedia = SPACEMETER_SIZE_703MB; } else if (!lstrcmp(lpstrCmdLine,_T("-burnimage"))) { return g_ActionManager.BurnImage(NULL,true); } else if (!lstrcmp(lpstrCmdLine,_T("-copyimage"))) { return g_ActionManager.CopyImage(NULL,true); } else if (!lstrcmp(lpstrCmdLine,_T("-tracks"))) { return g_ActionManager.ManageTracks(true); } else if (!lstrcmp(lpstrCmdLine,_T("-erase"))) { return g_ActionManager.Erase(NULL,true); } else if (!lstrcmp(lpstrCmdLine,_T("-fixate"))) { return g_ActionManager.Fixate(NULL,true); } else if (!lstrcmp(lpstrCmdLine,_T("-copydisc"))) { return g_ActionManager.CopyDisc(NULL,true); } // From the shell extension. else if (!lstrncmp(lpstrCmdLine,_T("-burnimage "),11)) { return g_ActionManager.BurnImageEx(NULL,true,lpstrCmdLine + 11); } else if (!lstrncmp(lpstrCmdLine,_T("-burnproject "),13)) { CWaitCursor WaitCursor; // This displays the hourglass cursor. if (g_ProjectManager.LoadProject(lpstrCmdLine + 13)) return g_ActionManager.BurnCompilation(NULL,true); return false; } #ifdef _DEBUG else if (!lstrncmp(lpstrCmdLine,SAVE_ENGLISH_STRINGS_PARAM,_countof(SAVE_ENGLISH_STRINGS_PARAM) - 1)) { return SaveEnglishStrings(lpstrCmdLine + _countof(SAVE_ENGLISH_STRINGS_PARAM) - 1); } #endif // General, open file. else if (lpstrCmdLine[0] != '\0') { TCHAR *szFullPath = new TCHAR[lstrlen(lpstrCmdLine) + 1]; // Strip quotes. if (lpstrCmdLine[0] == '\"') { lstrcpy(szFullPath,lpstrCmdLine + 1); szFullPath[lstrlen(szFullPath) - 1] = '\0'; } else { lstrcpy(szFullPath,lpstrCmdLine); } // Check what type of file that was specified. int iDelim = LastDelimiter(lpstrCmdLine,'.'); if (iDelim != -1) { // FIXME: Move this check to a common class for disc image management? if (!lstrcmpi(szFullPath + iDelim,_T(".iso")) || !lstrcmpi(szFullPath + iDelim,_T(".img")) || !lstrcmpi(szFullPath + iDelim,_T(".cue")) || !lstrcmpi(szFullPath + iDelim,_T(".bin")) || !lstrcmpi(szFullPath + iDelim,_T(".raw"))) return g_ActionManager.BurnImageEx(NULL,true,szFullPath); } g_pMainFrame->m_bDefaultWizard = false; lstrcpy(g_pMainFrame->m_szProjectFile,szFullPath); delete [] szFullPath; } return Run(lpstrCmdLine,nCmdShow); } int WINAPI _tWinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance,LPTSTR lpstrCmdLine,int nCmdShow) { try { #ifdef _DEBUG // In debug builds, generate a memory leak report on exit. _CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF); #endif // We need to call OleInitialize(), instead of CoInitialize(), // because the main frame will be calling RegisterDragDrop() later. HRESULT hRes = OleInitialize(NULL); if (!SUCCEEDED(hRes)) ckcore::throw_from_hresult(hRes,_T("Error during OleInitialize: " )); // This resolves ATL window thunking problem when Microsoft Layer for Unicode (MSLU) is used. ::DefWindowProc(NULL,0,0,0L); AtlInitCommonControls(ICC_COOL_CLASSES | ICC_BAR_CLASSES); hRes = _Module.Init(NULL,hInstance); ATLASSERT(SUCCEEDED(hRes)); INT_PTR nRet; CLogDlg LogDlg; // After LogDlg.Create() we must call LogDlg.DestroyWindow(), // even if an exception is thrown. Otherwise, the application // will crash on shutdown. try // Also acts as scope for variable 'MainFrame' etc. { // In order for it to work under Visual Studio 2005 Express / ATL 3.0, // the constructor for CMainFrame etc. must run after _Module.Init() has been // called, and the destructor must run before _Module.Term(). CMainFrame MainFrame; CProgressDlg ProgressDlg; CSimpleProgressDlg SimpleProgressDlg; CAboutWindow AboutWnd; g_pLogDlg = &LogDlg; g_pMainFrame = &MainFrame; g_pProgressDlg = &ProgressDlg; g_pSimpleProgressDlg = &SimpleProgressDlg; g_pAboutWnd = &AboutWnd; // Load the configuration. g_SettingsManager.Load(); // Create the log dialog. LogDlg.Create(HWND_DESKTOP); // Translate some of the string tables. lngTranslateTables(); // Initialize, SCSI buses etc. PerformDeviceScan(); // Load the codecs. TCHAR szCodecPath[MAX_PATH]; GetModuleFileName(NULL,szCodecPath,MAX_PATH - 1); ExtractFilePath(szCodecPath); lstrcat(szCodecPath,_T("codecs\\")); if (!g_CodecManager.LoadCodecs(szCodecPath)) { if (g_GlobalSettings.m_bCodecWarning) { CInfoDlg InfoDlg(&g_GlobalSettings.m_bCodecWarning,lngGetString(ERROR_LOADCODECS),INFODLG_NOCANCEL | INFODLG_ICONWARNING); InfoDlg.DoModal(); } } // Display the main window. nRet = ParseAndRun(lpstrCmdLine,nCmdShow); // Remove any temporary files. g_TempManager.CleanUp(); // Destroy the log dialog. if (LogDlg.IsWindow()) LogDlg.DestroyWindow(); } catch ( ... ) { // If someone tries to touch g_pMainFrame etc. after the object has been destroyed, // we need to find out. g_pLogDlg = NULL; g_pMainFrame = NULL; g_pProgressDlg = NULL; g_pSimpleProgressDlg = NULL; g_pAboutWnd = NULL; // Destroy the log dialog. if (LogDlg.IsWindow()) LogDlg.DestroyWindow(); _Module.Term(); OleUninitialize(); throw; } // If someone tries to touch g_pMainFrame etc. after the object has been destroyed, // we need to find out. g_pLogDlg = NULL; g_pMainFrame = NULL; g_pProgressDlg = NULL; g_pSimpleProgressDlg = NULL; g_pAboutWnd = NULL; _Module.Term(); OleUninitialize(); return (int)nRet; } catch (const std::exception &e) { ATLVERIFY(0 != MessageBox(NULL, ckcore::get_except_msg(e).c_str(), lngGetString(GENERAL_ERROR), MB_OK | MB_ICONERROR | MB_APPLMODAL)); return 1; } } void ProcessMessages() { MSG Msg; while (::PeekMessage(&Msg,NULL,0,0,PM_REMOVE)) { TranslateMessage(&Msg); DispatchMessage(&Msg); } } ================================================ FILE: src/app/infrarecorder.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include void ProcessMessages(); extern CCodecManager g_CodecManager; extern ckmmc::DeviceManager g_DeviceManager; ================================================ FILE: src/app/infrarecorder.rc ================================================ // Microsoft Visual C++ generated resource script. // #include "resource.h" #define APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 2 resource. // #include "atlres.h" ///////////////////////////////////////////////////////////////////////////// #undef APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // English (United States) resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US #pragma code_page(1252) #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 1 TEXTINCLUDE BEGIN "resource.h\0" END 2 TEXTINCLUDE BEGIN "#include ""atlres.h""\r\n" "\0" END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Menu // IDR_MAINFRAME MENU BEGIN POPUP "&File" BEGIN POPUP "&New Project" BEGIN MENUITEM "Data &CD", ID_NEWPROJECT_DATACD MENUITEM "Data CD (&multi-session)", ID_NEWPROJECT_DATACDMS MENUITEM "Data &DVD", ID_NEWPROJECT_DATADVD MENUITEM SEPARATOR MENUITEM "&Audio CD", ID_NEWPROJECT_AUDIO MENUITEM "Mi&xed-Mode CD", ID_NEWPROJECT_MIXED MENUITEM SEPARATOR MENUITEM "DVD-&Video Disc...", ID_NEWPROJECT_DVDVIDEO END MENUITEM "&Open Project...\tCtrl+O", ID_FILE_OPEN MENUITEM "&Save Project\tCtrl+S", ID_FILE_SAVE MENUITEM "Save Project &As...", ID_FILE_SAVE_AS MENUITEM SEPARATOR MENUITEM "Project &Properties...", ID_FILE_PROJECTPROPERTIES MENUITEM SEPARATOR MENUITEM "E&xit", ID_APP_EXIT END POPUP "&Edit" BEGIN MENUITEM "&New Folder", ID_EDIT_NEWFOLDER MENUITEM "Rena&me\tF2", ID_EDIT_RENAME MENUITEM "&Remove\tDel", ID_EDIT_REMOVE POPUP "&Add" BEGIN MENUITEM "&Selected", ID_ADD_SELECTED MENUITEM "&All", ID_ADD_ALL END MENUITEM "Im&port...", ID_EDIT_IMPORT MENUITEM SEPARATOR MENUITEM "Select &All\tCtrl+A", ID_EDIT_SELECTALL MENUITEM "&Invert Selection", ID_EDIT_INVERTSELECTION END POPUP "&Actions" BEGIN POPUP "Burn &Compilation" BEGIN MENUITEM "to a Compact &Disc...", ID_BURNCOMPILATION_COMPACTDISC MENUITEM "to a Disc &Image...", ID_BURNCOMPILATION_DISCIMAGE END MENUITEM "Burn &Image...", ID_ACTIONS_BURNIMAGE POPUP "C&opy Disc" BEGIN MENUITEM "to a Compact &Disc...", ID_COPYDISC_COMPACTDISC MENUITEM "to a Disc &Image...", ID_COPYDISC_DISCIMAGE END MENUITEM "&Manage Tracks...", ID_ACTIONS_MANAGETRACKS MENUITEM SEPARATOR MENUITEM "E&rase/Format Disc...", ID_ACTIONS_ERASERE MENUITEM "C&lose Disc...", ID_ACTIONS_FIXATEDISC MENUITEM SEPARATOR POPUP "Disc &Information" BEGIN MENUITEM "(no drives found)", ID_DISCINFORMATION_, GRAYED END MENUITEM "Import &Session...", ID_ACTIONS_IMPORTSESSION MENUITEM SEPARATOR POPUP "&Eject Disc" BEGIN MENUITEM "(no drives found)", ID_EJECTDISC_, GRAYED END END POPUP "&View" BEGIN POPUP "&Toolbars" BEGIN MENUITEM "&Standard Buttons", ID_VIEW_STANDARDTOOLBAR MENUITEM SEPARATOR MENUITEM "&Customize...", ID_VIEW_TBCUSTOMIZE END MENUITEM "&Status Bar", ID_VIEW_STATUS_BAR MENUITEM SEPARATOR MENUITEM "Program &Log...", ID_VIEW_PROGRAMLOG MENUITEM SEPARATOR MENUITEM "Lar&ge Icons", 32792 MENUITEM "S&mall Icons", 32793 MENUITEM "&List", 32794 MENUITEM "&Details", 32795 END POPUP "&Options" BEGIN MENUITEM "&Configuration...", ID_OPTIONS_CONFIGURATION MENUITEM "&Devices...", ID_OPTIONS_DEVICES END POPUP "&Help" BEGIN MENUITEM "&Help Topics", ID_HELP_HELPTOPICS MENUITEM SEPARATOR MENUITEM "&About InfraRecorder...", ID_APP_ABOUT END END ///////////////////////////////////////////////////////////////////////////// // // Icon // // Icon with lowest ID value placed first to ensure application icon // remains consistent on all systems. IDR_MAINFRAME ICON "Resources\\icon-main.ico" ///////////////////////////////////////////////////////////////////////////// // // Dialog // IDD_PROPPAGE_DEVICEGENERAL DIALOGEX 0, 0, 274, 234 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN ICON "",IDC_ICONSTATIC,7,7,21,20 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,31,259,1,WS_EX_STATICEDGE LTEXT "Static",IDC_NAMESTATIC,56,13,210,8 LTEXT "Type:",IDC_TYPELABELSTATIC,7,39,46,8 LTEXT "Location:",IDC_LOCATIONLABELSTATIC,7,54,46,8 LTEXT "Static",IDC_TYPESTATIC,56,39,210,8 LTEXT "Static",IDC_LOCATIONSTATIC,56,54,210,8 LTEXT "Buffer size:",IDC_BUFFERLABELSTATIC,7,70,45,8 LTEXT "Static",IDC_BUFFERSTATIC,56,70,210,8 CONTROL "",IDC_BEVELSTATIC2,"Static",SS_ETCHEDHORZ | WS_GROUP,7,86,259,1,WS_EX_STATICEDGE LTEXT "Maximum read speed:",IDC_MAXREADLABELSTATIC,7,93,259,8 LTEXT "Static",IDC_MAXREADSTATIC,12,103,254,8 LTEXT "Maximum write speed:",IDC_MAXWRITELABELSTATIC,7,118,259,8 LTEXT "Static",IDC_MAXWRITESTATIC,12,128,254,8 CONTROL "",IDC_BEVELSTATIC3,"Static",SS_ETCHEDHORZ | WS_GROUP,7,144,259,1,WS_EX_STATICEDGE LTEXT "Read:",IDC_READSTATIC,7,151,45,8 CONTROL "CD-R",IDC_READCDRCHECK,"Button",BS_3STATE | WS_TABSTOP,56,150,33,10 CONTROL "DVD-RAM",IDC_READDVDRAMCHECK,"Button",BS_3STATE | WS_TABSTOP,215,150,47,10 CONTROL "CD-RW",IDC_READCDRWCHECK,"Button",BS_3STATE | WS_TABSTOP,109,150,39,10 CONTROL "DVD-ROM",IDC_READDVDROMCHECK,"Button",BS_3STATE | WS_TABSTOP,56,163,47,10 CONTROL "DVD-R",IDC_READDVDRCHECK,"Button",BS_3STATE | WS_TABSTOP,162,150,37,10 LTEXT "Write:",IDC_WRITESTATIC,7,192,45,8 CONTROL "CD-R",IDC_WRITECDRCHECK,"Button",BS_3STATE | WS_TABSTOP,56,192,33,10 CONTROL "CD-RW",IDC_WRITECDRWCHECK,"Button",BS_3STATE | WS_TABSTOP,109,192,39,10 CONTROL "DVD-R",IDC_WRITEDVDRCHECK,"Button",BS_3STATE | WS_TABSTOP,162,192,37,10 CONTROL "DVD-RAM",IDC_WRITEDVDRAMCHECK,"Button",BS_3STATE | WS_TABSTOP,215,192,47,10 CONTROL "DVD+R",IDC_READDVDPLUSRCHECK,"Button",BS_3STATE | WS_TABSTOP,109,163,39,10 CONTROL "DVD+RW",IDC_READDVDPLUSRWCHECK,"Button",BS_3STATE | WS_TABSTOP,162,163,46,10 CONTROL "DVD+R DL",IDC_READDVDPLUSRDLCHECK,"Button",BS_3STATE | WS_TABSTOP,215,163,49,10 CONTROL "DVD+RW DL",IDC_READDVDPLUSRWDLCHECK,"Button",BS_3STATE | WS_TABSTOP,56,176,52,10 CONTROL "BD",IDC_READBDCHECK,"Button",BS_3STATE | WS_TABSTOP,109,176,25,10 CONTROL "HD-DVD",IDC_READHDDVDCHECK,"Button",BS_3STATE | WS_TABSTOP,162,176,41,10 CONTROL "DVD+R",IDC_WRITEDVDPLUSRCHECK,"Button",BS_3STATE | WS_TABSTOP,56,205,39,10 CONTROL "DVD+RW",IDC_WRITEDVDPLUSRWCHECK,"Button",BS_3STATE | WS_TABSTOP,109,205,46,10 CONTROL "DVD+R DL",IDC_WRITEDVDPLUSRDLCHECK,"Button",BS_3STATE | WS_TABSTOP,162,205,49,10 CONTROL "DVD+RW DL",IDC_WRITEDVDPLUSRWDLCHECK,"Button",BS_3STATE | WS_TABSTOP,215,205,56,10 CONTROL "BD",IDC_WRITEBDCHECK,"Button",BS_3STATE | WS_TABSTOP,56,218,25,10 CONTROL "HD-DVD",IDC_WRITEHDDVDCHECK,"Button",BS_3STATE | WS_TABSTOP,109,218,41,10 END IDD_PROPPAGE_DEVICEADVANCED DIALOGEX 0, 0, 274, 234 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "Advanced" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "Advanced information:",IDC_INFOSTATIC,7,7,90,8 CONTROL "",IDC_ADVLIST,"SysListView32",LVS_REPORT | LVS_ALIGNLEFT | LVS_NOCOLUMNHEADER | WS_BORDER | WS_TABSTOP,7,19,260,208 END IDD_PROPPAGE_BURNIMAGEGENERAL DIALOGEX 0, 0, 227, 196 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN ICON "",IDC_ICONSTATIC,7,7,20,20 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,31,213,1,WS_EX_STATICEDGE COMBOBOX IDC_RECORDERCOMBO,57,11,145,127,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Write speed:",IDC_WRITESPEEDSTATIC,7,72,49,8 COMBOBOX IDC_WRITESPEEDCOMBO,57,70,117,102,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Write method:",IDC_WRITEMETHODSTATIC,7,88,49,8 COMBOBOX IDC_WRITEMETHODCOMBO,57,86,117,86,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP CONTROL "",IDC_BEVELSTATIC2,"Static",SS_ETCHEDHORZ | WS_GROUP,8,120,212,1,WS_EX_STATICEDGE CONTROL "Eject the disc after writing",IDC_EJECTCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,127,213,10 CONTROL "Simulation",IDC_SIMULATECHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,140,213,10 CONTROL "Buffer underrun protection",IDC_BUPCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,153,213,10 CONTROL "Pad data tracks",IDC_PADCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,165,213,10 CONTROL "Close the disc after writing",IDC_FIXATECHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,178,213,10 CONTROL "On the fly",IDC_ONFLYCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,37,213,10 CONTROL "",IDC_BEVELSTATIC3,"Static",SS_ETCHEDHORZ | WS_GROUP,7,64,213,1,WS_EX_STATICEDGE CONTROL "Verify the disc after writing",IDC_VERIFYCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,50,213,10 PUSHBUTTON "",IDC_REFRESHBUTTON,206,11,14,13,BS_ICON LTEXT "Copies:",IDC_NUMCOPIESSTATIC,7,104,45,8 COMBOBOX IDC_NUMCOPIESCOMBO,57,103,48,30,CBS_DROPDOWN | WS_VSCROLL | WS_TABSTOP END IDD_PROPPAGE_BURNIMAGEADVANCED DIALOGEX 0, 0, 227, 134 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "Advanced" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN CONTROL "Allow overburning",IDC_OVERBURNCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,7,213,10 CONTROL "Swap audio byte order",IDC_SWABCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,19,213,10 CONTROL "Ignore medium size",IDC_IGNORESIZECHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,32,213,10 CONTROL "Set the SCSI IMMED flag",IDC_IMMEDCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,45,213,10 CONTROL "Yamaha Audio Master Q. R.",IDC_AUDIOMASTERCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,58,213,10 CONTROL "Forcespeed mode",IDC_FORCESPEEDCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,71,213,10 CONTROL "Plextor VariRec write mode",IDC_VARIRECCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,83,213,10 CONTROL "",IDC_VARIRECSLIDER,"msctls_trackbar32",TBS_AUTOTICKS | TBS_TOOLTIPS | WS_TABSTOP,7,96,100,20 EDITTEXT IDC_VARIRECEDIT,109,97,24,13,ES_AUTOHSCROLL | ES_READONLY END IDD_PROPPAGE_PROJECTPROPGENERAL DIALOGEX 0, 0, 226, 154 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN ICON "",IDC_ICONSTATIC,7,7,20,20 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,31,212,1,WS_EX_STATICEDGE LTEXT "Type:",IDC_TYPELABELSTATIC,7,38,49,8 EDITTEXT IDC_NAMEEDIT,57,11,162,13,ES_AUTOHSCROLL LTEXT "Size:",IDC_SIZELABELSTATIC,7,53,47,8 LTEXT "Contains:",IDC_CONTAINSLABELSTATIC,7,68,48,8 LTEXT "Static",IDC_TYPESTATIC,57,38,162,8 LTEXT "Static",IDC_SIZESTATIC,57,53,162,8 LTEXT "Static",IDC_CONTAINSSTATIC,57,68,162,8 END IDD_PROPPAGE_PROJECTPROPISO DIALOGEX 0, 0, 226, 154 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "ISO" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "Level:",IDC_LEVELSTATIC,7,9,50,8 COMBOBOX IDC_LEVELCOMBO,57,7,162,140,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,57,212,1,WS_EX_STATICEDGE CONTROL "Use Joliet file name extension",IDC_JOLIETCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,64,212,10 CONTROL "Allow more than 64 characters for Joliet names",IDC_JOLIETLONGNAMESCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,19,77,200,10 LTEXT "Format:",IDC_FORMATSTATIC,7,25,49,8 COMBOBOX IDC_FORMATCOMBO,57,23,162,108,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP CONTROL "Omit version numbers from ISO9660 file names",IDC_OMITVNCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,90,212,10 CONTROL "Allow more than 8 directories of path depth",IDC_DEEPDIRCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,103,212,10 COMBOBOX IDC_CHARSETCOMBO,57,39,162,108,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Character set:",IDC_CHARSETSTATIC,7,41,49,8 END IDD_PROPPAGE_PROJECTPROPFIELDS DIALOGEX 0, 0, 226, 154 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "Fields" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN EDITTEXT IDC_PUBLISHEREDIT,57,7,162,13,ES_AUTOHSCROLL LTEXT "Publisher:",IDC_PUBLISHERSTATIC,7,8,49,8 EDITTEXT IDC_PREPAREREDIT,57,23,162,13,ES_AUTOHSCROLL EDITTEXT IDC_SYSTEMEDIT,57,39,162,13,ES_AUTOHSCROLL EDITTEXT IDC_VOLUMEEDIT,57,55,162,13,ES_AUTOHSCROLL LTEXT "System:",IDC_SYSTEMSTATIC,7,40,47,8 LTEXT "Preparer:",IDC_PREPARERSTATIC,7,24,47,8 LTEXT "Volume set:",IDC_VOLUMESTATIC,7,56,48,8 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,72,212,1,WS_EX_STATICEDGE LTEXT "Copyright file:",IDC_COPYRIGHTSTATIC,7,80,49,8 EDITTEXT IDC_COPYRIGHTEDIT,57,78,162,13,ES_AUTOHSCROLL EDITTEXT IDC_ABSTRACTEDIT,57,94,162,13,ES_AUTOHSCROLL EDITTEXT IDC_BIBLIOGRAPHICEDIT,57,110,162,13,ES_AUTOHSCROLL LTEXT "Abstract file:",IDC_ABSTRACTSTATIC,7,96,49,8 LTEXT "Bibliographic...",IDC_BIBLIOGRAPHICSTATIC,7,112,49,8 END IDD_PROPPAGE_PROJECTPROPAUDIO DIALOGEX 0, 0, 226, 154 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "Audio" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "Album title:",IDC_ALBUMSTATIC,7,9,49,8 EDITTEXT IDC_ALBUMEDIT,57,7,161,13,ES_AUTOHSCROLL EDITTEXT IDC_ARTISTEDIT,57,23,161,13,ES_AUTOHSCROLL LTEXT "Artist:",IDC_ARTISTSTATIC,7,25,49,8 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,40,212,1,WS_EX_STATICEDGE CONTROL "",IDC_TRACKLIST,"SysListView32",LVS_REPORT | LVS_SINGLESEL | LVS_ALIGNLEFT | WS_BORDER | WS_TABSTOP,7,46,211,90 LTEXT "Double-click on a track to edit its settings.",IDC_INFOSTATIC,7,139,211,8 END IDD_PROPPAGE_CONFIGGENERAL DIALOGEX 0, 0, 247, 188 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN CONTROL "Check if autorun is enabled on each startup",IDC_AUTORUNCHECK, "Button",BS_AUTOCHECKBOX | WS_DISABLED | WS_TABSTOP,7,7,233,10 CONTROL "Remember the last active folder",IDC_REMEMBERSHELLCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,14,102,219,10 GROUPBOX "Explorer folder",IDC_SHELLFOLDERGROUPSTATIC,7,56,233,60 LTEXT "Enter the folder that you want to be the default folder in the explorer view part of the program.",IDC_SHELLFOLDERINFOSTATIC,14,66,218,18 EDITTEXT IDC_SHELLFOLDEREDIT,14,85,201,13,ES_AUTOHSCROLL PUSHBUTTON "...",IDC_SHELLFOLDERBROWSEBUTTON,220,85,14,13 CONTROL "Associate InfraRecorder with .irp (InfraRecorder Project) files",IDC_ASSOCIATECHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,32,233,10 GROUPBOX "Temporary folder",IDC_TEMPFOLDERGROUPSTATIC,7,119,233,49 LTEXT "The folder specified below will be used when data has to be temporarily stored on your harddrive.",IDC_TEMPFOLDERINFOSTATIC,14,129,218,18 EDITTEXT IDC_TEMPFOLDEREDIT,14,149,201,13,ES_AUTOHSCROLL PUSHBUTTON "...",IDC_TEMPFOLDERBROWSEBUTTON,220,149,14,13 CONTROL "Associate InfraRecorder with disc images (.iso, .img and .cue)",IDC_ASSOCIATEDISCIMAGECHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,45,233,10 CONTROL "Display welcome screen at startup",IDC_WIZARDCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,19,233,10 END IDD_PROPPAGE_CONFIGADVANCED DIALOGEX 0, 0, 247, 188 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "Advanced" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN CONTROL "Enable program log (not recomended for regular use)",IDC_LOGCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,7,233,10 GROUPBOX "FIFO buffer size",IDC_FIFOGROUPSTATIC,7,30,233,57 LTEXT "This option allows you to change the amount of memory that will be used as a RAM buffer. This is the secondary buffer in addition to your recorder's physical buffer.",IDC_FIFOINFOSTATIC,14,40,219,27 EDITTEXT IDC_FIFOEDIT,14,68,41,13,ES_AUTOHSCROLL,WS_EX_RIGHT LTEXT "MiB",IDC_FIFOMBSTATIC,59,70,12,8 CONTROL "Enable smoke effect (requires Windows Vista Aero)",IDC_SMOKECHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,19,233,10 END IDD_PROPPAGE_CONFIGLANGUAGE DIALOGEX 0, 0, 247, 188 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "Language" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "Language:",IDC_LANGUAGESTATIC,7,7,233,8 COMBOBOX IDC_LANGUAGECOMBO,7,18,131,163,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Please note that InfraRecorder needs to be restarted for new language settings to take affect.",IDC_LANGUAGEINFOSTATIC,7,39,233,24 END IDD_PROPPAGE_CONFIGSHELLEXT DIALOGEX 0, 0, 247, 188 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "Shell Extension" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN CONTROL "Enable InfraRecorder shell extension",IDC_SHELLEXTCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,7,233,10 CONTROL "Display context menu items in a submenu",IDC_SHELLEXTSUBMENUCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,19,233,10 LTEXT "Register the shell extension with the following file extensions:",IDC_SHELLEXTTEXTSTATIC,7,48,202,8 CONTROL "Display menu item icons",IDC_SHELLEXTICONCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,32,233,10 CONTROL "",IDC_SHELLEXTLIST,"SysListView32",LVS_REPORT | LVS_SINGLESEL | LVS_ALIGNLEFT | WS_BORDER | WS_TABSTOP,7,59,233,75 END IDD_PROPPAGE_COPYDISCGENERAL DIALOGEX 0, 0, 227, 210 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN COMBOBOX IDC_SOURCECOMBO,57,7,163,184,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Source:",IDC_SOURCESTATIC,7,9,49,8 COMBOBOX IDC_TARGETCOMBO,57,23,145,168,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Target:",IDC_TARGETSTATIC,7,24,49,8 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,40,213,1,WS_EX_STATICEDGE LTEXT "Write speed:",IDC_WRITESPEEDSTATIC,7,102,49,8 COMBOBOX IDC_WRITESPEEDCOMBO,57,100,117,103,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Write method:",IDC_WRITEMETHODSTATIC,7,118,49,8 COMBOBOX IDC_WRITEMETHODCOMBO,57,116,117,87,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP CONTROL "",IDC_BEVELSTATIC4,"Static",SS_ETCHEDHORZ | WS_GROUP,8,134,211,1,WS_EX_STATICEDGE CONTROL "Eject the disc after writing",IDC_EJECTCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,141,213,10 CONTROL "Simulation",IDC_SIMULATECHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,154,213,10 CONTROL "Buffer underrun protection",IDC_BUPCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,167,213,10 CONTROL "Pad data tracks",IDC_PADCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,180,213,10 CONTROL "Close the disc after writing",IDC_FIXATECHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,193,213,10 CONTROL "On the fly",IDC_ONFLYCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,47,213,10 CONTROL "",IDC_BEVELSTATIC5,"Static",SS_ETCHEDHORZ | WS_GROUP,7,94,211,1,WS_EX_STATICEDGE LTEXT "Copying on the fly is risky. Please make sure that your source device can read at least as fast as you will write.",IDC_ONFLYSTATIC,19,59,201,17 CONTROL "Clone disc (recommended)",IDC_CLONECHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,79,213,10 PUSHBUTTON "",IDC_REFRESHBUTTON,206,23,14,13,BS_ICON END IDD_PROPPAGE_DISCGENERAL DIALOGEX 0, 0, 227, 214 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN ICON "",IDC_ICONSTATIC,7,7,20,20 LTEXT "Static",IDC_NAMESTATIC,57,13,163,8 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,31,212,1,WS_EX_STATICEDGE LTEXT "Disc type:",IDC_TYPELABELSTATIC,7,39,49,8 LTEXT "Static",IDC_TYPESTATIC,57,39,163,8 LTEXT "Book type:",IDC_BOOKLABELSTATIC,7,54,49,8 LTEXT "Static",IDC_BOOKSTATIC,57,54,163,8 LTEXT "Region:",IDC_REGIONLABELSTATIC,7,70,48,8 LTEXT "Static",IDC_REGIONSTATIC,57,70,163,8 CONTROL "",IDC_BEVELSTATIC2,"Static",SS_ETCHEDHORZ | WS_GROUP,7,86,212,1,WS_EX_STATICEDGE LTEXT "Layers:",IDC_LAYERLABELSTATIC,7,94,47,8 LTEXT "Static",IDC_LAYERSTATIC,57,94,163,8 LTEXT "Static",IDC_TRACKSTATIC,57,110,163,8 LTEXT "Tracks:",IDC_TRACKLABELSTATIC,7,110,49,8 LTEXT "Static",IDC_SESSIONSTATIC,57,126,163,8 LTEXT "Sessions:",IDC_SESSIONLABELSTATIC,7,126,48,8 CONTROL "",IDC_BEVELSTATIC4,"Static",SS_ETCHEDHORZ | WS_GROUP,7,142,212,1,WS_EX_STATICEDGE LTEXT "Static",IDC_STATUSSTATIC,57,150,163,17 LTEXT "Status:",IDC_STATUSLABELSTATIC,7,150,49,8 CONTROL "",IDC_BEVELSTATIC5,"Static",SS_ETCHEDHORZ | WS_GROUP,7,174,211,1,WS_EX_STATICEDGE LTEXT "Used space:",IDC_USEDSPACELABELSTATIC,7,182,50,8 LTEXT "Static",IDC_USEDSPACESTATIC,57,182,163,8 LTEXT "Static",IDC_FREESPACESTATIC,57,198,163,8 LTEXT "Free space:",IDC_FREESPACELABELSTATIC,7,198,49,8 END IDD_PROPPAGE_READOPTIONS DIALOGEX 0, 0, 227, 158 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "Read" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN CONTROL "Ignore read errors",IDC_NOREADERRCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,7,213,10 CONTROL "Read all sub-channel data and the full TOC",IDC_READSUBCHANNELCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,19,213,10 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,32,212,1,WS_EX_STATICEDGE LTEXT "Read speed:",IDC_READSPEEDSTATIC,7,40,50,8 COMBOBOX IDC_READSPEEDCOMBO,57,38,117,113,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP END IDD_PROPPAGE_COPYIMAGEGENERAL DIALOGEX 0, 0, 227, 139 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "Source:",IDC_SOURCESTATIC,7,9,49,8 PUSHBUTTON "...",IDC_BROWSEBUTTON,206,23,14,13 COMBOBOX IDC_SOURCECOMBO,57,7,145,90,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Image file:",IDC_IMAGESTATIC,7,24,45,8 EDITTEXT IDC_IMAGEEDIT,57,23,145,13,ES_AUTOHSCROLL | ES_READONLY PUSHBUTTON "",IDC_REFRESHBUTTON,206,7,14,13,BS_ICON END IDD_PROPPAGE_PROJECTPROPBOOT DIALOGEX 0, 0, 226, 153 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "Boot" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "Boot images:",IDC_BOOTSTATIC,7,7,131,8 CONTROL "",IDC_LIST,"SysListView32",LVS_REPORT | LVS_SINGLESEL | LVS_ALIGNLEFT | WS_BORDER | WS_TABSTOP,7,18,212,108 END IDD_PROPPAGE_PROJECTPROPFILESYS DIALOGEX 0, 0, 226, 154 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "File System" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "File system:",IDC_FILESYSSTATIC,7,9,50,8 COMBOBOX IDC_FILESYSCOMBO,57,7,162,140,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP END IDD_PROPPAGE_PROJECTPROPUDF DIALOGEX 0, 0, 226, 154 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "UDF" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "Version:",IDC_VERSIONSTATIC,7,9,50,8 COMBOBOX IDC_VERSIONCOMBO,57,7,162,140,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP END ///////////////////////////////////////////////////////////////////////////// // // DESIGNINFO // #ifdef APSTUDIO_INVOKED GUIDELINES DESIGNINFO BEGIN IDD_PROPPAGE_DEVICEGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 266 TOPMARGIN, 7 BOTTOMMARGIN, 227 END IDD_PROPPAGE_DEVICEADVANCED, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 267 TOPMARGIN, 7 BOTTOMMARGIN, 227 END IDD_PROPPAGE_BURNIMAGEGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 220 TOPMARGIN, 7 BOTTOMMARGIN, 189 END IDD_PROPPAGE_BURNIMAGEADVANCED, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 220 TOPMARGIN, 7 BOTTOMMARGIN, 127 END IDD_PROPPAGE_PROJECTPROPGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 219 TOPMARGIN, 7 BOTTOMMARGIN, 147 END IDD_PROPPAGE_PROJECTPROPISO, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 219 TOPMARGIN, 7 BOTTOMMARGIN, 147 END IDD_PROPPAGE_PROJECTPROPFIELDS, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 219 TOPMARGIN, 7 BOTTOMMARGIN, 147 END IDD_PROPPAGE_PROJECTPROPAUDIO, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 218 TOPMARGIN, 7 BOTTOMMARGIN, 147 END IDD_PROPPAGE_CONFIGGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 240 TOPMARGIN, 7 BOTTOMMARGIN, 181 END IDD_PROPPAGE_CONFIGADVANCED, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 240 TOPMARGIN, 7 BOTTOMMARGIN, 181 END IDD_PROPPAGE_CONFIGLANGUAGE, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 240 TOPMARGIN, 7 BOTTOMMARGIN, 181 END IDD_PROPPAGE_CONFIGSHELLEXT, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 240 TOPMARGIN, 7 BOTTOMMARGIN, 181 END IDD_PROPPAGE_COPYDISCGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 220 TOPMARGIN, 7 BOTTOMMARGIN, 203 END IDD_PROPPAGE_DISCGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 220 TOPMARGIN, 7 BOTTOMMARGIN, 207 END IDD_PROPPAGE_READOPTIONS, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 220 TOPMARGIN, 7 BOTTOMMARGIN, 151 END IDD_PROPPAGE_COPYIMAGEGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 220 TOPMARGIN, 7 BOTTOMMARGIN, 132 END IDD_PROPPAGE_PROJECTPROPBOOT, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 219 TOPMARGIN, 7 BOTTOMMARGIN, 146 END IDD_PROPPAGE_PROJECTPROPFILESYS, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 219 TOPMARGIN, 7 BOTTOMMARGIN, 147 END IDD_PROPPAGE_PROJECTPROPUDF, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 219 TOPMARGIN, 7 BOTTOMMARGIN, 147 END END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Accelerator // IDR_MAINFRAME ACCELERATORS BEGIN VK_DELETE, ID_EDIT_REMOVE, VIRTKEY, NOINVERT VK_F2, ID_EDIT_RENAME, VIRTKEY, NOINVERT "O", ID_FILE_OPEN, VIRTKEY, CONTROL, NOINVERT "P", ID_FILE_PRINT, VIRTKEY, CONTROL, NOINVERT "S", ID_FILE_SAVE, VIRTKEY, CONTROL, NOINVERT VK_F6, ID_NEXT_PANE, VIRTKEY, NOINVERT VK_F6, ID_PREV_PANE, VIRTKEY, SHIFT, NOINVERT "V", ID_SHELL_PASTE, VIRTKEY, CONTROL, NOINVERT "A", ID_EDIT_SELECTALL, VIRTKEY, CONTROL, NOINVERT END ///////////////////////////////////////////////////////////////////////////// // // Version // VS_VERSION_INFO VERSIONINFO FILEVERSION 0,53,0,0 PRODUCTVERSION 0,53,0,0 FILEFLAGSMASK 0x3fL #ifdef _DEBUG FILEFLAGS 0x1L #else FILEFLAGS 0x0L #endif FILEOS 0x4L FILETYPE 0x2L FILESUBTYPE 0x0L BEGIN BLOCK "StringFileInfo" BEGIN BLOCK "040904b0" BEGIN VALUE "CompanyName", "Christian Kindahl" VALUE "FileDescription", "InfraRecorder" VALUE "FileVersion", "0.53.0.0" VALUE "InternalName", "InfraRecorder" VALUE "LegalCopyright", "Copyright 2006-2012 Christian Kindahl" VALUE "OriginalFilename", "InfraRecorder.exe" VALUE "ProductName", "InfraRecorder" VALUE "ProductVersion", "0.53.0.0" END END BLOCK "VarFileInfo" BEGIN VALUE "Translation", 0x409, 1200 END END ///////////////////////////////////////////////////////////////////////////// // // String Table // STRINGTABLE BEGIN IDR_MAINFRAME "InfraRecorder" ID_VIEW_UPLEVEL "Go up one level." ID_TRACK_READ "Save the selected track(s) to your hard drive." ID_TRACK_VERIFY "Scan the selected track(s) for errors." ID_TRACK_ERASE "Erase the selected track(s) from the disc." ID_SHELLEXT_ADD "Add a new file extension to the list." ID_SHELLEXT_REMOVE "Remove the selected file extension from the list." ID_BOOT_ADD "Add a new boot image to the project." ID_BOOT_REMOVE "Remove the selected boot image from the project." ID_BOOT_EDIT "Edit the selected boot image." ID_NEWPROJECT_DATA "Create a new data project." END STRINGTABLE BEGIN ID_FILE_OPEN "Open an existing project." ID_FILE_CLOSE "Close the active document\nClose" ID_FILE_SAVE "Save the active project." ID_FILE_SAVE_AS "Save the active project with a new name." ID_FILE_PAGE_SETUP "Change the printing options\nPage Setup" END STRINGTABLE BEGIN ID_APP_ABOUT "Display program information, version number and copyright." ID_APP_EXIT "Quit the application." END STRINGTABLE BEGIN ID_NEXT_PANE "Switch to the next window pane\nNext Pane" ID_PREV_PANE "Switch back to the previous window pane\nPrevious Pane" END STRINGTABLE BEGIN ID_VIEW_TOOLBAR "Show or hide the toolbar.\nToggle ToolBar" ID_VIEW_STATUS_BAR "Show or hide the status bar.\nToggle StatusBar" END STRINGTABLE BEGIN ATL_IDS_SCSIZE "Change the window size" ATL_IDS_SCMOVE "Change the window position" ATL_IDS_SCMINIMIZE "Reduce the window to an icon" ATL_IDS_SCMAXIMIZE "Enlarge the window to full size" ATL_IDS_SCNEXTWINDOW "Switch to the next document window" ATL_IDS_SCPREVWINDOW "Switch to the previous document window" ATL_IDS_SCCLOSE "Close the active window and prompts to save the documents" END STRINGTABLE BEGIN ATL_IDS_SCRESTORE "Restore the window to normal size" ATL_IDS_SCTASKLIST "Activate Task List" ATL_IDS_MDICHILD "Activate this window" END STRINGTABLE BEGIN ATL_IDS_IDLEMESSAGE "Ready" END STRINGTABLE BEGIN ATL_IDS_MRU_FILE "Open this document" END STRINGTABLE BEGIN ID_ACTIONS_ERASERE "Erase or format a disc." ID_VIEW_PROGRAMLOG "View the program log." ID_ACTIONS_BURNIMAGE "Write the contents of a disc-image to a CD." ID_OPTIONS_CONFIGURATION "Configure InfraRecorder." ID_OPTIONS_DEVICES "View device properties and edit the device configuration." END STRINGTABLE BEGIN ID_NEWPROJECT_DATACD "Create a new data CD project." ID_NEWPROJECT_AUDIO "Create a new audio CD project." ID_NEWPROJECT_MIXED "Create a new mixed-mode CD project." ID_EDIT_NEWFOLDER "Add a new folder to the project." ID_EDIT_RENAME "Rename the selected item." ID_EDIT_REMOVE "Remove the selected item(s) from the project." END STRINGTABLE BEGIN ID_FILE_PROJECTPROPERTIES "Display and change project settings." ID_BURNCOMPILATION_DISCIMAGE "Burn the current compilation to a disc image." ID_BURNCOMPILATION_COMPACTDISC "Burn the current compilation to a physical compact disc." ID_ACTIONS_FIXATEDISC "Close a disc that has not already been closed." ID_ACTIONS_MANAGETRACKS "View disc track layout, save tracks and verify tracks." ID_COPYDISC_COMPACTDISC "Copy the contents of a CD directly to another CD." ID_COPYDISC_DISCIMAGE "Copy the contents of a CD to a disc image." END STRINGTABLE BEGIN ID_ADD_SELECTED "Add the selected object(s) to the project." ID_ADD_ALL "Add all object(s) to the project." ID_ACTIONS_DISCINFORMATION "Display disc information." ID_ACTIONS_IMPORTSESSION "Import an existing session to your current project." ID_HELP_HELPTOPICS "Display help topics." ID_NEWPROJECT_DVDVIDEO "Create a new DVD-Video disc project." ID_NEWPROJECT_DATADVD "Create a new data DVD project." END STRINGTABLE BEGIN ID_EDIT_SELECTALL "Select all items in the window." ID_EDIT_INVERTSELECTION "Reverse which items are selected and which are not." ID_NEWPROJECT_DATACDMS "Create a new multi-session data CD project." ID_EDIT_IMPORT "Import file(s) to the project." END #endif // English (United States) resources ///////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////// // Swedish (Sweden) resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_SVE) LANGUAGE LANG_SWEDISH, SUBLANG_SWEDISH #pragma code_page(1252) #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 3 TEXTINCLUDE BEGIN "\r\0" END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Menu // IDR_PROJLISTSELMENU MENU BEGIN POPUP "Popup Menu" BEGIN MENUITEM "Rena&me", ID_EDIT_RENAME MENUITEM "&Remove", ID_EDIT_REMOVE MENUITEM SEPARATOR MENUITEM "&Properties...", ID_POPUPMENU_PROPERTIES END END IDR_PROJLISTNOSELMENU MENU BEGIN POPUP "Popup Menu" BEGIN POPUP "&View" BEGIN MENUITEM "Lar&ge Icons", 32792 MENUITEM "S&mall Icons", 32793 MENUITEM "&List", 32794 MENUITEM "&Details", 32795 END MENUITEM SEPARATOR MENUITEM "&New Folder", ID_EDIT_NEWFOLDER END END IDR_SHELLTREEMENU MENU BEGIN POPUP "Popup Menu" BEGIN MENUITEM "&Properties", ID_POPUPMENU_SHELLTREE_PROPERTIES END END IDR_DIAGNOSTICSMENU MENU BEGIN POPUP "" BEGIN MENUITEM "&Device Scan", ID_DIAGNOSTICS_DEVICESCAN END END ///////////////////////////////////////////////////////////////////////////// // // Icon // // Icon with lowest ID value placed first to ensure application icon // remains consistent on all systems. IDI_MIXEDICON ICON "Resources\\project-mixed.ico" IDI_AUDIOICON ICON "Resources\\project-audio.ico" IDI_DATAICON ICON "Resources\\project-data.ico" IDI_VIDEOICON ICON "Resources\\project-video.ico" IDI_PROJECTICON ICON "Resources\\icon-project.ico" IDI_REFRESHICON ICON "Resources\\icon-refresh.ico" ///////////////////////////////////////////////////////////////////////////// // // Dialog // IDD_PROGRESSDLG DIALOGEX 0, 0, 338, 143 STYLE DS_SETFONT | DS_FIXEDSYS | WS_MAXIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,225,122,50,14 PUSHBUTTON "Cancel",IDCANCEL,281,122,50,14 CONTROL "",IDC_TOTALPROGRESS,"msctls_progress32",WS_BORDER,7,18,324,9 LTEXT "",IDC_TOTALSTATIC,7,7,324,8 CONTROL "",IDC_MESSAGELIST,"SysListView32",LVS_REPORT | LVS_SHAREIMAGELISTS | LVS_ALIGNLEFT | LVS_NOSORTHEADER | WS_BORDER | WS_TABSTOP,7,47,324,50 LTEXT "",IDC_STATUSSTATIC,7,36,324,8 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,103,324,1,WS_EX_STATICEDGE LTEXT "",IDC_DEVICESTATIC,7,107,324,8 LTEXT "Write-buffer:",IDC_BUFFERSTATIC,13,117,44,8 CONTROL "",IDC_BUFFERPROGRESS,"msctls_progress32",WS_BORDER,59,117,86,9 PUSHBUTTON "Reload",IDC_RELOADBUTTON,170,122,50,14,NOT WS_VISIBLE END IDD_SIMPLEPROGRESSDLG DIALOGEX 0, 0, 338, 108 STYLE DS_SETFONT | DS_FIXEDSYS | WS_MAXIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,225,87,50,14 PUSHBUTTON "Cancel",IDCANCEL,281,87,50,14 CONTROL "",IDC_MESSAGELIST,"SysListView32",LVS_REPORT | LVS_SHAREIMAGELISTS | LVS_ALIGNLEFT | LVS_NOSORTHEADER | WS_BORDER | WS_TABSTOP,7,18,324,50 LTEXT "",IDC_STATUSSTATIC,7,7,324,8 CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7,73,324,1,WS_EX_STATICEDGE LTEXT "",IDC_DEVICESTATIC,7,78,324,8 PUSHBUTTON "Reload",IDC_RELOADBUTTON,170,87,50,14,NOT WS_VISIBLE END IDD_ERASEDLG DIALOGEX 0, 0, 250, 115 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "Erase/Format Disc" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,193,7,50,14 PUSHBUTTON "Cancel",IDCANCEL,193,24,50,14 LTEXT "Recorder:",IDC_RECORDERSTATIC,7,7,177,8 COMBOBOX IDC_RECORDERCOMBO,7,18,161,90,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Erase method:",IDC_METHODSTATIC,7,39,123,8 COMBOBOX IDC_METHODCOMBO,7,50,124,58,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP CONTROL "Ignore illegal TOC (force erase)",IDC_FORCECHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,72,236,10 CONTROL "Eject the disc after erasing",IDC_EJECTCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,85,236,10 CONTROL "Simulation",IDC_SIMULATECHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,98,236,10 PUSHBUTTON "Help",IDC_HELPBUTTON,193,41,50,14 PUSHBUTTON "",IDC_REFRESHBUTTON,172,18,14,13,BS_ICON COMBOBOX IDC_SPEEDCOMBO,135,50,51,58,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Speed:",IDC_SPEEDSTATIC,135,39,51,8 END IDD_LOGDLG DIALOGEX 0, 0, 320, 147 STYLE DS_SETFONT | DS_FIXEDSYS | WS_MINIMIZEBOX | WS_MAXIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME CAPTION "Program Log" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,263,7,50,14 PUSHBUTTON "Save &As...",ID_SAVEASBUTTON,263,126,50,14 EDITTEXT IDC_LOGEDIT,7,7,249,133,ES_MULTILINE | ES_AUTOVSCROLL | ES_AUTOHSCROLL | ES_READONLY | WS_VSCROLL PUSHBUTTON "&Diagnostics",IDC_DIAGNOSTICSBUTTON,263,24,50,14 PUSHBUTTON "&Files",IDC_FILESBUTTON,263,41,50,14 END IDD_DEVICESDLG DIALOGEX 0, 0, 305, 105 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "Devices" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,248,7,50,14 CONTROL "",IDC_DEVICELIST,"SysListView32",LVS_REPORT | LVS_SINGLESEL | LVS_ALIGNLEFT | LVS_NOSORTHEADER | WS_BORDER | WS_TABSTOP,7,18,234,80 LTEXT "Double-click on a device to view its detailed information.",IDC_INFOSTATIC,7,7,219,8 PUSHBUTTON "Rescan",IDC_RESCANBUTTON,248,84,50,14 PUSHBUTTON "Help",IDC_HELPBUTTON,248,24,50,14 END IDD_WAITDLG DIALOGEX 0, 0, 145, 51 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN CTEXT "",IDC_INFOSTATIC,7,7,131,37,SS_CENTERIMAGE END IDD_EDITTRACKDLG DIALOGEX 0, 0, 240, 70 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,183,7,50,14 PUSHBUTTON "Cancel",IDCANCEL,183,24,50,14 LTEXT "Track title:",IDC_TITLESTATIC,7,7,169,8 LTEXT "Artist name:",IDC_ARTISTSTATIC,7,39,169,8 EDITTEXT IDC_TITLEEDIT,7,18,169,13,ES_AUTOHSCROLL EDITTEXT IDC_ARTISTEDIT,7,50,169,13,ES_AUTOHSCROLL END IDD_FIXATEDLG DIALOGEX 0, 0, 250, 70 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "Close Disc" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,193,7,50,14 PUSHBUTTON "Cancel",IDCANCEL,193,24,50,14 LTEXT "Recorder:",IDC_RECORDERSTATIC,7,7,179,8 COMBOBOX IDC_RECORDERCOMBO,7,18,179,45,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP CONTROL "Eject the disc after closing",IDC_EJECTCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,40,178,10 CONTROL "Simulation",IDC_SIMULATECHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,53,178,10 PUSHBUTTON "Help",IDC_HELPBUTTON,193,41,50,14 END IDD_TRACKSDLG DIALOGEX 0, 0, 251, 161 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "Tracks" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "Close",IDOK,194,7,50,14 LTEXT "Device:",IDC_DRIVESTATIC,7,7,179,8 CONTROL "",IDC_TRACKLIST,"SysListView32",LVS_REPORT | LVS_SHAREIMAGELISTS | LVS_ALIGNLEFT | WS_BORDER | WS_TABSTOP,7,36,179,103 PUSHBUTTON "Help",IDC_HELPBUTTON,194,24,50,14 COMBOBOX IDC_DEVICECOMBO,7,18,179,144,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP END IDD_NEWFILEEXTDLG DIALOGEX 0, 0, 240, 70 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "New File Extension" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,183,7,50,14 PUSHBUTTON "Cancel",IDCANCEL,183,24,50,14 LTEXT "Description:",IDC_DESCSTATIC,7,7,170,8 EDITTEXT IDC_DESCEDIT,7,18,169,13,ES_AUTOHSCROLL LTEXT "File extensions (separated by a comma):",IDC_EXTSTATIC,7,39,169,8 EDITTEXT IDC_EXTEDIT,7,50,170,13,ES_AUTOHSCROLL END IDD_INFODLG DIALOGEX 0, 0, 281, 60 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,224,7,50,14 PUSHBUTTON "Cancel",IDCANCEL,224,24,50,14 ICON "",IDC_ICONSTATIC,7,7,20,20 LTEXT "",IDC_INFOSTATIC,33,7,185,34 CONTROL "Do not display this message again",IDC_DISPLAYMSGCHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,33,43,186,10 END IDD_IMPORTSESSIONDLG DIALOGEX 0, 0, 250, 85 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "Import Session" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,193,7,50,14 PUSHBUTTON "Cancel",IDCANCEL,193,24,50,14 LTEXT "Device:",IDC_DRIVESTATIC,7,7,179,8 COMBOBOX IDC_DEVICECOMBO,7,18,179,45,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP LTEXT "Static",IDC_USEDSPACESTATIC,73,70,170,8 LTEXT "Used space:",IDC_USEDSPACELABELSTATIC,7,70,64,8 LTEXT "Track to import:",IDC_TRACKSTATIC,7,38,179,8 COMBOBOX IDC_TRACKCOMBO,7,49,179,45,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP END IDD_SAVETRACKSDLG DIALOGEX 0, 0, 240, 70 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "Save Tracks" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,183,7,50,14 PUSHBUTTON "Cancel",IDCANCEL,183,24,50,14 LTEXT "Target folder:",IDC_TARGETSTATIC,7,7,46,8 EDITTEXT IDC_TARGETEDIT,7,18,150,13,ES_AUTOHSCROLL LTEXT "Audio track output format:",IDC_AUDIOFORMATSTATIC,7,39,86,8 COMBOBOX IDC_AUDIOFORMATCOMBO,7,50,109,85,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP PUSHBUTTON "...",IDC_BROWSEBUTTON,162,18,14,13 PUSHBUTTON "Settings...",IDC_AUDIOFORMATBUTTON,121,50,55,13 END IDD_ADDBOOTIMAGEDLG DIALOGEX 0, 0, 240, 103 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "Add Boot Image" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "OK",IDOK,183,7,50,14 PUSHBUTTON "Cancel",IDCANCEL,183,24,50,14 LTEXT "Emulation type:",IDC_EMULATIONSTATIC,7,7,168,8 COMBOBOX IDC_EMULATIONCOMBO,7,18,91,30,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP GROUPBOX "Advanced options",IDC_OPTIONSSTATIC,7,39,169,57 CONTROL "Don't make image bootable",IDC_NOBOOTCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,14,50,158,10 EDITTEXT IDC_BOOTSEGMENTEDIT,90,61,80,13,ES_AUTOHSCROLL,WS_EX_RIGHT PUSHBUTTON "Help",IDC_HELPBUTTON,183,41,50,14 LTEXT "Boot load size:",IDC_BOOTSIZESTATIC,14,78,74,8 EDITTEXT IDC_BOOTSIZEEDIT,90,77,80,13,ES_AUTOHSCROLL,WS_EX_RIGHT LTEXT "Boot load segment:",IDC_BOOTSEGMENTSTATIC,14,62,75,8 END IDD_CONFIRMFILEREPLACEDLG DIALOGEX 0, 0, 286, 122 STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION | WS_SYSMENU CAPTION "Confirm File Replace" FONT 8, "MS Shell Dlg", 400, 0, 0x1 BEGIN DEFPUSHBUTTON "No",IDC_NOBUTTON,145,101,50,14 PUSHBUTTON "No to All",IDC_NOALLBUTTON,199,101,50,14 PUSHBUTTON "Yes",IDC_YESBUTTON,37,101,50,14 PUSHBUTTON "Yes to All",IDC_YESALLBUTTON,91,101,50,14 ICON "",IDC_ICONSTATIC,7,7,21,20 LTEXT "The target folder already contains a file named:",IDC_INFOSTATIC,33,7,246,22 LTEXT "Would you like to replace the existing file",IDC_REPLACEINFOSTATIC,33,29,246,8 ICON "",IDC_OLDICONSTATIC,36,40,21,20 LTEXT "",IDC_OLDSIZESTATIC,62,41,217,8 LTEXT "",IDC_OLDDATESTATIC,62,51,217,8 LTEXT "with this one?",IDC_REPLACEINFO2STATIC,33,63,228,8 ICON "",IDC_NEWICONSTATIC,36,74,21,20 LTEXT "",IDC_NEWSIZESTATIC,62,75,217,8 LTEXT "",IDC_NEWDATESTATIC,62,85,217,8 END ///////////////////////////////////////////////////////////////////////////// // // DESIGNINFO // #ifdef APSTUDIO_INVOKED GUIDELINES DESIGNINFO BEGIN IDD_PROGRESSDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 331 TOPMARGIN, 7 BOTTOMMARGIN, 136 END IDD_SIMPLEPROGRESSDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 331 TOPMARGIN, 7 BOTTOMMARGIN, 101 END IDD_ERASEDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 243 TOPMARGIN, 7 BOTTOMMARGIN, 108 END IDD_LOGDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 313 TOPMARGIN, 7 BOTTOMMARGIN, 140 END IDD_DEVICESDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 298 TOPMARGIN, 7 BOTTOMMARGIN, 98 END IDD_WAITDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 138 TOPMARGIN, 7 BOTTOMMARGIN, 44 END IDD_EDITTRACKDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 233 TOPMARGIN, 7 BOTTOMMARGIN, 63 END IDD_FIXATEDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 243 TOPMARGIN, 7 BOTTOMMARGIN, 63 END IDD_TRACKSDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 244 TOPMARGIN, 7 BOTTOMMARGIN, 154 END IDD_NEWFILEEXTDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 233 TOPMARGIN, 7 BOTTOMMARGIN, 63 END IDD_INFODLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 274 TOPMARGIN, 7 BOTTOMMARGIN, 53 END IDD_IMPORTSESSIONDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 243 TOPMARGIN, 7 BOTTOMMARGIN, 78 END IDD_SAVETRACKSDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 233 TOPMARGIN, 7 BOTTOMMARGIN, 63 END IDD_ADDBOOTIMAGEDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 233 TOPMARGIN, 7 BOTTOMMARGIN, 96 END IDD_CONFIRMFILEREPLACEDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 279 TOPMARGIN, 7 BOTTOMMARGIN, 115 END END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // PNG // IDR_WELCOMELOGOPNG PNG "Resources\\background-welcome_logo.png" IDR_BUTTONFPNG PNG "Resources\\Buttons\\button-focus.png" IDR_BUTTONHPNG PNG "Resources\\Buttons\\button-hover.png" IDR_BUTTONHFPNG PNG "Resources\\Buttons\\button-hover_focus.png" IDR_BUTTONNPNG PNG "Resources\\Buttons\\button-normal.png" IDR_MBUTTONFPNG PNG "Resources\\Buttons\\multi_button-focus.png" IDR_MBUTTONHPNG PNG "Resources\\Buttons\\multi_button-hover.png" IDR_MBUTTONHFPNG PNG "Resources\\Buttons\\multi_button-hover_focus.png" IDR_MBUTTONHFS1PNG PNG "Resources\\Buttons\\multi_button-hover_focus_specific1.png" IDR_MBUTTONHFS2PNG PNG "Resources\\Buttons\\multi_button-hover_focus_specific2.png" IDR_MBUTTONHS1PNG PNG "Resources\\Buttons\\multi_button-hover_specific1.png" IDR_MBUTTONHS2PNG PNG "Resources\\Buttons\\multi_button-hover_specific2.png" IDR_MBUTTONNPNG PNG "Resources\\Buttons\\multi_button-normal.png" IDR_WIZARDAUDIOPNG PNG "Resources\\Wizard\\icon-audio_disc.png" IDR_WIZARDCOPYPNG PNG "Resources\\Wizard\\icon-copy_disc.png" IDR_WIZARDDATAPNG PNG "Resources\\Wizard\\icon-data_disc.png" IDR_WIZARDREADPNG PNG "Resources\\Wizard\\icon-read_disc.png" IDR_WIZARDVIDEOPNG PNG "Resources\\Wizard\\icon-video_disc.png" IDR_WIZARDWRITEPNG PNG "Resources\\Wizard\\icon-write_image.png" ///////////////////////////////////////////////////////////////////////////// // // Bitmap // IDB_SPLASHBITMAP BITMAP "Resources\\background-splash.bmp" IDB_MINITOOLBARBITMAP BITMAP "Resources\\toolbar-mini.bmp" IDB_MINITOOLBARBITMAP_ BITMAP "Resources\\toolbar-mini_.bmp" IDB_TRACKTOOLBARBITMAP BITMAP "Resources\\toolbar-track.bmp" IDB_TRACKTOOLBARBITMAP_ BITMAP "Resources\\toolbar-track_.bmp" IDB_MAINSMALLBITMAP BITMAP "Resources\\toolbar-main_small.bmp" IDB_MAINSMALLBITMAP_ BITMAP "Resources\\toolbar-main_small_.bmp" IDB_MAINLARGEBITMAP BITMAP "Resources\\toolbar-main_large.bmp" IDB_MAINLARGEBITMAP_ BITMAP "Resources\\toolbar-main_large_.bmp" IDB_PANECLOSEBITMAP BITMAP "Resources\\button-close.bmp" IDB_ABOUTBITMAP BITMAP "Resources\\background-about.bmp" #endif // Swedish (Sweden) resources ///////////////////////////////////////////////////////////////////////////// #ifndef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 3 resource. // ///////////////////////////////////////////////////////////////////////////// #endif // not APSTUDIO_INVOKED ================================================ FILE: src/app/infrarecorder_vc08.vcproj ================================================ ================================================ FILE: src/app/infrarecorder_vc10.vcxproj ================================================  Debug Win32 Debug x64 ReleaseP Win32 ReleaseP x64 Release Win32 Release x64 Template Win32 Template x64 infrarecorder {949B73FF-BD75-47C0-B965-328513C481B4} infrarecorder Application Unicode Application Unicode Application Unicode Application Application Unicode Application Unicode Application Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKMMCDIR)\include\;$(CKROOTDIR)\ckmmc\include\;$(CKFILESYSTEMDIR)\include\;$(CKROOTDIR)\ckfilesystem\include\;$(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKMMCDIR)\include\;$(CKROOTDIR)\ckmmc\include\;$(CKFILESYSTEMDIR)\include\;$(CKROOTDIR)\ckfilesystem\include\;$(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKMMCDIR)\include\;$(CKROOTDIR)\ckmmc\include\;$(CKFILESYSTEMDIR)\include\;$(CKROOTDIR)\ckfilesystem\include\;$(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKMMCDIR)\include\;$(CKROOTDIR)\ckmmc\include\;$(CKFILESYSTEMDIR)\include\;$(CKROOTDIR)\ckfilesystem\include\;$(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKMMCDIR)\lib64\;$(CKROOTDIR)\ckmmc\lib64\;$(CKFILESYSTEMDIR)\lib64\;$(CKROOTDIR)\ckfilesystem\lib64\;$(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKMMCDIR)\include\;$(CKROOTDIR)\ckmmc\include\;$(CKFILESYSTEMDIR)\include\;$(CKROOTDIR)\ckfilesystem\include\;$(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKMMCDIR)\lib64\;$(CKROOTDIR)\ckmmc\lib64\;$(CKFILESYSTEMDIR)\lib64\;$(CKROOTDIR)\ckfilesystem\lib64\;$(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKMMCDIR)\include\;$(CKROOTDIR)\ckmmc\include\;$(CKFILESYSTEMDIR)\include\;$(CKROOTDIR)\ckfilesystem\include\;$(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKMMCDIR)\lib64\;$(CKROOTDIR)\ckmmc\lib64\;$(CKFILESYSTEMDIR)\lib64\;$(CKROOTDIR)\ckfilesystem\lib64\;$(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKMMCDIR)\lib\;$(CKROOTDIR)\ckmmc\lib\;$(CKFILESYSTEMDIR)\lib\;$(CKROOTDIR)\ckfilesystem\lib\;$(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKMMCDIR)\lib\;$(CKROOTDIR)\ckmmc\lib\;$(CKFILESYSTEMDIR)\lib\;$(CKROOTDIR)\ckfilesystem\lib\;$(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKMMCDIR)\lib\;$(CKROOTDIR)\ckmmc\lib\;$(CKFILESYSTEMDIR)\lib\;$(CKROOTDIR)\ckfilesystem\lib\;$(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) _DEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)infrarecorder.tlb infrarecorder.h infrarecorder_i.c infrarecorder_p.c Disabled $(ProjectDir);$(ProjectDir)control\;$(ProjectDir)core\;$(ProjectDir)dialog\;$(ProjectDir)utility\;$(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;_DEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_SECURE_NO_DEPRECATE;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level4 EditAndContinue _DEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) htmlhelp.lib;winmm.lib;ckcored.lib;ckfilesystemd.lib;ckmmcd.lib;libpng15.lib;zlib.lib;%(AdditionalDependencies) true Windows MachineX86 _DEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)infrarecorder.tlb infrarecorder.h infrarecorder_i.c infrarecorder_p.c Disabled $(ProjectDir);$(ProjectDir)control\;$(ProjectDir)core\;$(ProjectDir)dialog\;$(ProjectDir)utility\;$(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;_DEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_SECURE_NO_DEPRECATE;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level4 ProgramDatabase _DEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) htmlhelp.lib;winmm.lib;ckcored.lib;ckfilesystemd.lib;ckmmcd.lib;libpng15.lib;zlib.lib;%(AdditionalDependencies) true Windows MachineX64 NDEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)infrarecorder.tlb infrarecorder.h infrarecorder_i.c infrarecorder_p.c MaxSpeed $(ProjectDir);$(ProjectDir)control\;$(ProjectDir)core\;$(ProjectDir)dialog\;$(ProjectDir)utility\;$(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;NDEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_SECURE_NO_DEPRECATE;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) false Sync Default MultiThreaded true Use Level3 NDEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) htmlhelp.lib;winmm.lib;ckcore.lib;ckfilesystem.lib;ckmmc.lib;libpng15.lib;zlib.lib;%(AdditionalDependencies) Windows MachineX86 NDEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)infrarecorder.tlb infrarecorder.h infrarecorder_i.c infrarecorder_p.c MaxSpeed $(ProjectDir);$(ProjectDir)control\;$(ProjectDir)core\;$(ProjectDir)dialog\;$(ProjectDir)utility\;$(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;NDEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_SECURE_NO_DEPRECATE;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) false Sync Default MultiThreaded true Use Level3 NDEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) htmlhelp.lib;winmm.lib;ckcore.lib;ckfilesystem.lib;ckmmc.lib;libpng15.lib;zlib.lib;%(AdditionalDependencies) Windows MachineX64 NDEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)infrarecorder.tlb infrarecorder.h infrarecorder_i.c infrarecorder_p.c MaxSpeed $(ProjectDir);$(ProjectDir)control\;$(ProjectDir)core\;$(ProjectDir)dialog\;$(ProjectDir)utility\;$(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;NDEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_SECURE_NO_DEPRECATE;_CRT_NON_CONFORMING_SWPRINTFS;PORTABLE;%(PreprocessorDefinitions) false Sync Default MultiThreaded true Use Level3 NDEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) htmlhelp.lib;winmm.lib;ckcore.lib;ckfilesystem.lib;ckmmc.lib;libpng15.lib;zlib.lib;%(AdditionalDependencies) Windows MachineX86 NDEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)infrarecorder.tlb infrarecorder.h infrarecorder_i.c infrarecorder_p.c MaxSpeed $(ProjectDir);$(ProjectDir)control\;$(ProjectDir)core\;$(ProjectDir)dialog\;$(ProjectDir)utility\;$(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;NDEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_SECURE_NO_DEPRECATE;_CRT_NON_CONFORMING_SWPRINTFS;PORTABLE;%(PreprocessorDefinitions) false Sync Default MultiThreaded true Use Level3 NDEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) htmlhelp.lib;winmm.lib;ckcore.lib;ckfilesystem.lib;ckmmc.lib;libpng15.lib;zlib.lib;%(AdditionalDependencies) Windows MachineX64 stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh {81ea1bb3-2ba0-4600-9081-2d2cb9203466} false ================================================ FILE: src/app/infrarecorder_vc10.vcxproj.filters ================================================  {d85c6bed-28d6-420b-af8f-ede0217d10dc} cpp;c;cxx;def;odl;idl;hpj;bat;asm {1f2547c6-c107-48fd-95f8-6b902e5496cd} {b9d0e8e3-351c-4a30-ad56-adda8e3d77fe} {1d87a704-ef86-428c-9275-904ca3cdb4bc} {fcb35f20-d0bf-4159-8263-ca8767d27618} {e901b0d8-2399-4d03-8b03-a1c9a3d7cb9d} h;hpp;hxx;hm;inl;inc {f5fe78e4-6571-4719-b9c7-2d8dc16f1de2} {71c00cda-4259-42b7-b432-6f42bc3b1c0e} {730528af-b1b8-4eb3-99a5-8c22fb865ba2} {2594990d-46e8-42f3-aa59-15d435e67ea8} {781d6da1-ed1a-48c5-aa4b-f8ce12a3af5d} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;jpg;jpeg;jpe;manifest Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\control Source Files\core Source Files\core Source Files\core Source Files\core Source Files\core Source Files\core Source Files\core Source Files\core Source Files\core Source Files\core Source Files\core Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\dialog Source Files\utility Source Files\utility Source Files\utility Source Files\utility Source Files\utility Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\control Header Files\core Header Files\core Header Files\core Header Files\core Header Files\core Header Files\core Header Files\core Header Files\core Header Files\core Header Files\core Header Files\core Header Files\core Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\dialog Header Files\utility Header Files\utility Header Files\utility Header Files\utility Header Files\utility Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Resource Files Header Files Resource Files ================================================ FILE: src/app/pidl_helper.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "pidl_helper.hh" CPidlHelper::CPidlHelper() { if (FAILED(SHGetMalloc(&m_spMalloc))) m_spMalloc = NULL; } CPidlHelper::~CPidlHelper() { } /* CPidlHelper::FreePidl --------------------- Frees the pidl using ILFree. It assumes that the pidl has been allocated using ILClone or its equivalent. */ void CPidlHelper::FreePidl(LPITEMIDLIST &pidl) { // FIXME: Use CoTaskMemFree(pidl); on Windows 2000 and newer. ILFree(pidl); pidl = NULL; } /* CPidlHelper::Split ------------------ Splits the pidl into a parent pidl and a relative child pidl. The caller is responsible for freeing the pidls created. The function returns true if the pidls where successfully created, false otherwise. */ bool CPidlHelper::Split(LPCITEMIDLIST pidl,LPITEMIDLIST *pParent,LPITEMIDLIST *pChild) { if (pParent) { *pParent = NULL; ILRemoveLastID(*pParent = ILClone(pidl)); if (!*pParent) return false; } if (pChild) { *pChild = NULL; *pChild = ILClone(ILFindLastID(pidl)); if (!*pChild) { ILFree(*pParent); return false; } } return true; } /* CPidlHelper::GetPathName ------------------------ Puts iMaxLength number of bits of the pidls name into szPathName. It assumes that pidl is a single SHITEMID that belongs to pParent. It return true if no errors occured, false otherwise. */ bool CPidlHelper::GetPathName(IShellFolder *pParent,LPCITEMIDLIST pidl, TCHAR *szPathName,int iMaxLength) { if (!pidl || !pParent) return false; STRRET strret; if (FAILED(pParent->GetDisplayNameOf(pidl,SHGDN_FORPARSING/* | SHGDN_FORADDRESSBAR*/,&strret))) return false; // Get pidl from name. return STRRET2TCHAR(pidl,&strret,szPathName,iMaxLength); } /* CPidlHelper::GetDisplayPathName ------------------------------- Puts iMaxLength number of bits of the pidls display name into szPathName. It assumes that pidl is a single SHITEMID that belongs to pParent. It return true if no errors occured, false otherwise. */ bool CPidlHelper::GetDisplayPathName(IShellFolder *pParent,LPCITEMIDLIST pidl, TCHAR *szPathName,int iMaxLength) { if (!pidl || !pParent) return false; STRRET strret; if (FAILED(pParent->GetDisplayNameOf(pidl,SHGDN_FORPARSING | SHGDN_FORADDRESSBAR,&strret))) return false; return STRRET2TCHAR(pidl,&strret,szPathName,iMaxLength); } /* CPidlHelper::GetPathName ------------------------ Puts the pidls name into szPathName. It return true if no errors occured, false otherwise. */ bool CPidlHelper::GetPathName(LPCITEMIDLIST pidl,TCHAR *szPathName) { if (!pidl) return false; SHGetPathFromIDList(pidl,szPathName); if (!lstrlen(szPathName)) return false; return true; } /* CPidlHelper::GetPidl -------------------- Generates a pidl from a path name. The function returns true if no errors occured, otherwise it returns false. */ bool CPidlHelper::GetPidl(TCHAR *szPathName,LPITEMIDLIST *ppidl) { CComBSTR cbsPath(szPathName); USES_CONVERSION; LPWSTR wszPath = const_cast(T2CW(szPathName)); //HRVERIFY(wszPath); CComPtrspShellFolder; SHGetDesktopFolder(&spShellFolder); ULONG dwEaten; spShellFolder->ParseDisplayName(0,0,wszPath,&dwEaten,ppidl,0); return (ppidl != NULL); } /* CPidlHelper::strret2TCHAR ------------------------- Converts a STREET structure to a TCHAR string of iMaxChars length. It assumes that szTarget is a buffer large enough to contain the string. True is returned upong success, false otherwise. */ bool CPidlHelper::STRRET2TCHAR(LPCITEMIDLIST pidl,STRRET *psr,TCHAR *szTarget, int iMaxChars,bool bFreeOleStr) { USES_CONVERSION; if (!m_spMalloc) return false; TCHAR *pszTmp = NULL; switch (psr->uType) { case STRRET_WSTR: pszTmp = W2T(psr->pOleStr); /*if (bFreeOleStr) m_spMalloc->Free(psr->pOleStr);*/ break; case STRRET_OFFSET: pszTmp = A2T((char *)pidl + psr->uOffset); break; case STRRET_CSTR: pszTmp = A2T(psr->cStr); break; } if (pszTmp != NULL) { lstrcpyn(szTarget,pszTmp,iMaxChars); // The ole-string can't be freed before we have copied the result string. if (psr->uType == STRRET_WSTR && bFreeOleStr) m_spMalloc->Free(psr->pOleStr); } return NULL != pszTmp; } LPITEMIDLIST CPidlHelper::CreatePidl(unsigned int uiSize) { LPITEMIDLIST pidl = NULL; IMalloc* pMalloc; if (FAILED(SHGetMalloc(&pMalloc))) return false; pidl = (LPITEMIDLIST)pMalloc->Alloc(uiSize); if (pidl) ZeroMemory(pidl,uiSize); pMalloc->Release(); return pidl; } ITEMIDLIST *CPidlHelper::GetNextPidlItem(LPCITEMIDLIST pidl) { if (pidl) return (ITEMIDLIST *)(BYTE *)(((BYTE *)pidl) + pidl->mkid.cb); else return NULL; } unsigned int CPidlHelper::GetPidlSize(LPCITEMIDLIST pidl) { unsigned int uiTotal = 0; ITEMIDLIST *pidlTemp = (ITEMIDLIST *)pidl; if (pidlTemp) { while (pidlTemp->mkid.cb) { uiTotal += pidlTemp->mkid.cb; pidlTemp = GetNextPidlItem(pidlTemp); } // Requires a 16 bit zero value for the NULL terminator. uiTotal += 2 * sizeof(BYTE); } return uiTotal; } LPITEMIDLIST CPidlHelper::ConcatenatePidl(LPCITEMIDLIST pidl1,LPCITEMIDLIST pidl2) { LPITEMIDLIST pidlNew; unsigned int cb1 = 0,cb2 = 0; if (pidl1) cb1 = GetPidlSize(pidl1) - (2 * sizeof(BYTE)); cb2 = GetPidlSize(pidl2); pidlNew = CreatePidl(cb1 + cb2); if (pidlNew) { if (pidl1) CopyMemory(pidlNew, pidl1, cb1); CopyMemory(((LPBYTE)pidlNew) + cb1, pidl2, cb2); } return pidlNew; } ================================================ FILE: src/app/pidl_helper.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CPidlHelper { protected: CComPtr m_spMalloc; private: LPITEMIDLIST CreatePidl(unsigned int uiSize); ITEMIDLIST *GetNextPidlItem(LPCITEMIDLIST pidl); unsigned int GetPidlSize(LPCITEMIDLIST pidl); public: CPidlHelper(); virtual ~CPidlHelper(); bool GetPathName(IShellFolder *pParent,LPCITEMIDLIST pidl,TCHAR *szPathName,int iMaxLength = MAX_PATH); bool GetDisplayPathName(IShellFolder *pParent,LPCITEMIDLIST pidl,TCHAR *szPathName,int iMaxLength = MAX_PATH); bool GetPathName(LPCITEMIDLIST pidl,TCHAR *szPathName); bool GetPidl(TCHAR *szPathName,LPITEMIDLIST *ppidl); bool Split(LPCITEMIDLIST pidl,LPITEMIDLIST *pParent,LPITEMIDLIST *pChild); bool STRRET2TCHAR(LPCITEMIDLIST pidl,STRRET *psr,TCHAR *szTarget,int iMaxChars = MAX_PATH,bool bFreeOleStr = true); void FreePidl(LPITEMIDLIST &pidl); LPITEMIDLIST ConcatenatePidl(LPCITEMIDLIST pidl1,LPCITEMIDLIST pidl2); }; ================================================ FILE: src/app/png_file.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "resource.h" #include "png_file.hh" #include // FIXME: Recent versions of libpng hides functionality used by this class. CPngFile::CPngFile() : m_ulWidth(0),m_ulHeight(0),m_pRowData(NULL) { } CPngFile::~CPngFile() { Close(); } void CPngFile::ReadMemFile(png_structp pPng,png_bytep pData,png_size_t iSize) { CMemFile *pMemFile = (CMemFile *)pPng->io_ptr; if (pMemFile->m_iRemainBytes >= iSize) { memcpy(pData,pMemFile->m_pData,iSize); pMemFile->m_pData += iSize; pMemFile->m_iRemainBytes -= iSize; } else { png_error(pPng,"io error"); } } bool CPngFile::Open(unsigned short usResourceId) { HRSRC hPngResource = FindResource(NULL,MAKEINTRESOURCE(usResourceId),_T("PNG")); if (hPngResource == NULL) return false; unsigned long ulSize = SizeofResource(NULL,hPngResource); HGLOBAL hPngData = LoadResource(NULL,hPngResource); unsigned char *pData = (unsigned char *)LockResource(hPngData); if (pData == NULL) return false; // Read the data. CMemFile MemFile(pData,ulSize); // Create data structures. png_structp pRead = png_create_read_struct(PNG_LIBPNG_VER_STRING,0,0,0); png_infop pInfo = png_create_info_struct(pRead); png_set_read_fn(pRead,&MemFile,ReadMemFile); // Read entire image. png_read_png(pRead,pInfo,PNG_TRANSFORM_EXPAND,0); if (pInfo->valid & PNG_INFO_IDAT && pInfo->pixel_depth == 32) { m_ulWidth = pInfo->width; m_ulHeight = pInfo->height; m_pRowData = pInfo->row_pointers; pInfo->row_pointers = NULL; for (unsigned long y = 0; y < m_ulHeight; y++) { unsigned char *pRowData = m_pRowData[y]; for (unsigned long x = 0; x < m_ulWidth; x++) { pRowData[0] = (pRowData[0] * pRowData[3]) / 255; pRowData[1] = (pRowData[1] * pRowData[3]) / 255; pRowData[2] = (pRowData[2] * pRowData[3]) / 255; pRowData[3] = ~pRowData[3]; pRowData += 4; } } png_destroy_read_struct(&pRead,&pInfo,0); GlobalUnlock(hPngData); return true; } png_destroy_read_struct(&pRead,&pInfo,0); GlobalUnlock(hPngData); return true; } bool CPngFile::Open(const TCHAR *szFullPath) { FILE *pFile = _wfopen(szFullPath,_T("rb")); if (pFile == NULL) return false; // Create data structures. png_structp pRead = png_create_read_struct(PNG_LIBPNG_VER_STRING,0,0,0); png_infop pInfo = png_create_info_struct(pRead); png_init_io(pRead,pFile); // Read entire image. png_read_png(pRead,pInfo,PNG_TRANSFORM_EXPAND,0); fclose(pFile); if (pInfo->valid & PNG_INFO_IDAT && pInfo->pixel_depth == 32) { m_ulWidth = pInfo->width; m_ulHeight = pInfo->height; m_pRowData = pInfo->row_pointers; pInfo->row_pointers = NULL; for (unsigned long y = 0; y < m_ulHeight; y++) { unsigned char *pData = m_pRowData[y]; for (unsigned long x = 0; x < m_ulWidth; x++) { pData[0] = (pData[0] * pData[3]) / 255; pData[1] = (pData[1] * pData[3]) / 255; pData[2] = (pData[2] * pData[3]) / 255; pData[3] = ~pData[3]; pData += 4; } } png_destroy_read_struct(&pRead,&pInfo,0); return true; } png_destroy_read_struct(&pRead,&pInfo,0); return false; } bool CPngFile::Close() { if (m_pRowData == NULL) return false; // FIXME: This does not work if libpng is linked dynamically. Maybe look into // saving the pInfo structure and free it with png_destroy_read_struct // here. for (unsigned long y = 0; y < m_ulHeight; y++) free(m_pRowData[y]); free(m_pRowData); return true; } bool CPngFile::Draw(HDC hDC,int iX,int iY,int iWidth,int iHeight) { if (iWidth > (int)m_ulWidth) iWidth = m_ulWidth; if (iHeight > (int)m_ulHeight) iHeight = m_ulHeight; if (iWidth == 0 || iHeight == 0) return false; HDC hMemDC = NULL; HBITMAP hDestBitmap = NULL,hOldBitmap = NULL; unsigned char *pDestBits = NULL; unsigned char **pRowData = m_pRowData + m_ulHeight - 1 - (m_ulHeight - iHeight); //Do alpla blend int iLineTailDest = (((24 * iWidth) + 31) / 32 * 4) - 3 * iWidth; BITMAPINFO bmi; ZeroMemory(&bmi,sizeof(bmi)); bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); bmi.bmiHeader.biWidth = iWidth; bmi.bmiHeader.biHeight = iHeight; bmi.bmiHeader.biPlanes = 1; bmi.bmiHeader.biBitCount = 24; bmi.bmiHeader.biCompression = BI_RGB; // Create device context. hMemDC = CreateCompatibleDC(hDC); hDestBitmap = CreateDIBSection(hDC,&bmi,DIB_RGB_COLORS,(void **)&pDestBits,NULL,0); hOldBitmap = (HBITMAP)SelectObject(hMemDC,hDestBitmap); BitBlt(hMemDC,0,0,iWidth,iHeight,hDC,iX,iY,SRCCOPY); BYTE *p1 = pDestBits; for (int y = 0; y < iHeight; y++) { BYTE *p2 = *(pRowData--); for (int x = 0; x < iWidth; x++) { *p1++ = ((p2[3] * (*p1)) >> 8) + p2[2]; // B *p1++ = ((p2[3] * (*p1)) >> 8) + p2[1]; // G *p1++ = ((p2[3] * (*p1)) >> 8) + p2[0]; // R p2 += 4; } p1 += iLineTailDest; } // Render. BitBlt(hDC,iX,iY,iWidth,iHeight,hMemDC,0,0,SRCCOPY); SelectObject(hMemDC,hOldBitmap); //Free memory. DeleteObject(hDestBitmap); DeleteDC(hMemDC); return true; } ================================================ FILE: src/app/png_file.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include class CPngFile { private: class CMemFile { public: unsigned char *m_pData; size_t m_iRemainBytes; CMemFile(unsigned char *pData,size_t iRemainBytes) : m_pData(pData),m_iRemainBytes(iRemainBytes) { } }; unsigned long m_ulWidth; unsigned long m_ulHeight; unsigned char **m_pRowData; static void ReadMemFile(png_structp pPng,png_bytep pData,png_size_t iSize); public: CPngFile(); ~CPngFile(); bool Open(unsigned short usResourceId); bool Open(const TCHAR *szFullPath); bool Close(); bool Draw(HDC hDC,int iX,int iY,int iWidth,int iHeight); }; ================================================ FILE: src/app/project_data_object.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_data_object.hh" #include "enum_fmt_etc.hh" CProjectDataObject::CProjectDataObject() { // Reference count must ALWAYS start at 1. m_lRefCount = 1; memset(&m_FormatEtc,0,sizeof(m_FormatEtc)); m_FormatEtc.cfFormat = static_cast(::RegisterClipboardFormat(_T(PROJECT_CF_NAME))); m_FormatEtc.dwAspect = DVASPECT_CONTENT; m_FormatEtc.lindex = 0; m_FormatEtc.ptd = NULL; m_FormatEtc.tymed = TYMED_HGLOBAL; memset(&m_StgMedium,0,sizeof(m_StgMedium)); m_StgMedium.tymed = TYMED_HGLOBAL; // No files have yet been extracted. m_bOperationPerformed = false; m_pParent = NULL; } CProjectDataObject::~CProjectDataObject() { ReleaseStgMedium(&m_StgMedium); } void CProjectDataObject::Reset() { m_bOperationPerformed = false; m_FileItems.clear(); } void CProjectDataObject::AddFile(CItemData *pFileItem) { m_FileItems.push_back(pFileItem); } void CProjectDataObject::SetParent(CProjectNode *pParent) { m_pParent = pParent; } bool CProjectDataObject::IsFormatSupported(FORMATETC *pFormatEtc) { if (m_FormatEtc.cfFormat == pFormatEtc->cfFormat && m_FormatEtc.dwAspect == pFormatEtc->dwAspect && m_FormatEtc.tymed & pFormatEtc->tymed) { return true; } return false; } HRESULT __stdcall CProjectDataObject::QueryInterface(REFIID iid,void **ppvObject) { // Check to see what interface has been requested. if (iid == IID_IDataObject || iid == IID_IUnknown) { AddRef(); *ppvObject = this; return S_OK; } else { *ppvObject = 0; return E_NOINTERFACE; } } ULONG __stdcall CProjectDataObject::AddRef() { // Increment object reference count. return InterlockedIncrement(&m_lRefCount); } ULONG __stdcall CProjectDataObject::Release() { // Decrement object reference count. LONG lCount = InterlockedDecrement(&m_lRefCount); if (lCount == 0) { delete this; return 0; } else { return lCount; } } HRESULT __stdcall CProjectDataObject::GetData(FORMATETC *pFormatEtc,STGMEDIUM *pStgMedium) { if (!IsFormatSupported(pFormatEtc)) return DV_E_FORMATETC; // Copy the storage medium data. pStgMedium->tymed = m_StgMedium.tymed; pStgMedium->pUnkForRelease = 0; pStgMedium->hGlobal = GlobalAlloc(GMEM_SHARE,sizeof(CProjectDropData) + sizeof(CItemData *) * m_FileItems.size()); CProjectDropData *pDropData = (CProjectDropData *)GlobalLock(pStgMedium->hGlobal); pDropData->m_pParent = m_pParent; pDropData->m_ppData = (CItemData **)(pDropData + sizeof(CProjectDropData)); // Copy the file names into the global memory. unsigned int uiPos = 0; std::vector::const_iterator it; for (it = m_FileItems.begin(); it != m_FileItems.end(); it++) pDropData->m_ppData[uiPos++] = (CItemData *)*it; GlobalUnlock(pDropData); return S_OK; } HRESULT CProjectDataObject::GetDataHere(FORMATETC *pFormatEtc,STGMEDIUM *pMedium) { return DATA_E_FORMATETC; } HRESULT __stdcall CProjectDataObject::QueryGetData(FORMATETC *pFormatEtc) { return IsFormatSupported(pFormatEtc) ? S_OK : DV_E_FORMATETC; } HRESULT CProjectDataObject::GetCanonicalFormatEtc(FORMATETC *pFormatEct,FORMATETC *pFormatEtcOut) { // MUST be set to NULL. pFormatEtcOut->ptd = NULL; return E_NOTIMPL; } HRESULT __stdcall CProjectDataObject::SetData(FORMATETC *pFormatEtc,STGMEDIUM *pMedium,BOOL fRelease) { return E_NOTIMPL; } HRESULT __stdcall CProjectDataObject::EnumFormatEtc(DWORD dwDirection,IEnumFORMATETC **ppEnumFormatEtc) { if (dwDirection == DATADIR_GET) { // Windows 2000 and newer only. //return SHCreateStdEnumFmtEtc(1,&m_FormatEtc,ppEnumFormatEtc); return CreateEnumFmtEtc(1,&m_FormatEtc,ppEnumFormatEtc); } else { return E_NOTIMPL; } } HRESULT CProjectDataObject::DAdvise(FORMATETC *pFormatEtc,DWORD advf,IAdviseSink *pAdvSink, DWORD *pdwConnection) { return OLE_E_ADVISENOTSUPPORTED; } HRESULT CProjectDataObject::DUnadvise(DWORD dwConnection) { return OLE_E_ADVISENOTSUPPORTED; } HRESULT CProjectDataObject::EnumDAdvise(IEnumSTATDATA **ppEnumAdvise) { return OLE_E_ADVISENOTSUPPORTED; } ================================================ FILE: src/app/project_data_object.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "tree_manager.hh" #define PROJECT_CF_NAME "IRPROJECT" class CProjectDropData { public: CProjectNode *m_pParent; CItemData **m_ppData; }; class CProjectDataObject : public IDataObject { private: bool m_bOperationPerformed; long m_lRefCount; FORMATETC m_FormatEtc; STGMEDIUM m_StgMedium; std::vector m_FileItems; CProjectNode *m_pParent; bool IsFormatSupported(FORMATETC *pFormatEtc); public: CProjectDataObject(); ~CProjectDataObject(); void Reset(); void AddFile(CItemData *pFileItem); void SetParent(CProjectNode *pParent); // IUnknown members. HRESULT __stdcall QueryInterface(REFIID iid,void **ppvObject); ULONG __stdcall AddRef(); ULONG __stdcall Release(); // IDataObject members. HRESULT __stdcall GetData(FORMATETC *pFormatEtc,STGMEDIUM *pmedium); HRESULT __stdcall GetDataHere(FORMATETC *pFormatEtc,STGMEDIUM *pmedium); HRESULT __stdcall QueryGetData(FORMATETC *pFormatEtc); HRESULT __stdcall GetCanonicalFormatEtc(FORMATETC *pFormatEct,FORMATETC *pFormatEtcOut); HRESULT __stdcall SetData(FORMATETC *pFormatEtc,STGMEDIUM *pMedium,BOOL fRelease); HRESULT __stdcall EnumFormatEtc(DWORD dwDirection, IEnumFORMATETC **ppEnumFormatEtc); HRESULT __stdcall DAdvise(FORMATETC *pFormatEtc,DWORD advf,IAdviseSink *,DWORD *); HRESULT __stdcall DUnadvise(DWORD dwConnection); HRESULT __stdcall EnumDAdvise(IEnumSTATDATA **ppEnumAdvise); }; ================================================ FILE: src/app/project_drop_source.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_drop_source.hh" CProjectDropSource::CProjectDropSource() { m_lRefCount = 1; } CProjectDropSource::~CProjectDropSource() { } HRESULT __stdcall CProjectDropSource::QueryInterface(REFIID iid,void **ppvObject) { // Check to see what interface has been requested. if (iid == IID_IDropSource || iid == IID_IUnknown) { AddRef(); *ppvObject = this; return S_OK; } else { *ppvObject = 0; return E_NOINTERFACE; } } ULONG __stdcall CProjectDropSource::AddRef() { // Increment object reference count. return InterlockedIncrement(&m_lRefCount); } ULONG __stdcall CProjectDropSource::Release() { // Decrement object reference count. LONG lCount = InterlockedDecrement(&m_lRefCount); if (lCount == 0) { delete this; return 0; } else { return lCount; } } HRESULT __stdcall CProjectDropSource::QueryContinueDrag(BOOL fEscapePressed,DWORD grfKeyState) { // If the escape key has been pressed we cancel the operation. if (fEscapePressed == TRUE) return DRAGDROP_S_CANCEL; // If the left button has been released we should drop. if ((grfKeyState & MK_LBUTTON) == 0) return DRAGDROP_S_DROP; return S_OK; } HRESULT __stdcall CProjectDropSource::GiveFeedback(DWORD dwEffect) { return DRAGDROP_S_USEDEFAULTCURSORS; } ================================================ FILE: src/app/project_drop_source.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CProjectDropSource : public IDropSource { private: long m_lRefCount; public: CProjectDropSource(); ~CProjectDropSource(); // IUnknown members. HRESULT __stdcall QueryInterface(REFIID iid,void ** ppvObject); ULONG __stdcall AddRef(); ULONG __stdcall Release(); // IDropSource members. HRESULT __stdcall QueryContinueDrag(BOOL fEscapePressed,DWORD grfKeyState); HRESULT __stdcall GiveFeedback(DWORD dwEffect); }; ================================================ FILE: src/app/project_drop_target_base.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "project_drop_target_base.hh" #include "project_data_object.hh" CProjectDropTargetBase::CProjectDropTargetBase() { m_uiClipFormat = ::RegisterClipboardFormat(_T(PROJECT_CF_NAME)); m_lRefCount = 1; } CProjectDropTargetBase::~CProjectDropTargetBase() { } HRESULT __stdcall CProjectDropTargetBase::QueryInterface(REFIID iid,void **ppvObject) { // Check to see what interface has been requested. if (iid == IID_IDropTarget || iid == IID_IUnknown) { AddRef(); *ppvObject = this; return S_OK; } else { *ppvObject = 0; return E_NOINTERFACE; } } ULONG __stdcall CProjectDropTargetBase::AddRef() { // Increment object reference count. return InterlockedIncrement(&m_lRefCount); } ULONG __stdcall CProjectDropTargetBase::Release() { // Decrement object reference count. LONG lCount = InterlockedDecrement(&m_lRefCount); if (lCount == 0) { delete this; return 0; } else { return lCount; } } CProjectDropTargetBase::eDropType CProjectDropTargetBase::QueryDataObject(IDataObject *pDataObject) { FORMATETC fmtetc = { CF_HDROP,0,DVASPECT_CONTENT,-1,TYMED_HGLOBAL }; if (pDataObject->QueryGetData(&fmtetc) == S_OK) return DT_HDROP; fmtetc.cfFormat = static_cast(m_uiClipFormat); if (pDataObject->QueryGetData(&fmtetc) == S_OK) return DT_IRPROJECT; return DT_NONE; } HRESULT __stdcall CProjectDropTargetBase::DragEnter(IDataObject *pDataObject,DWORD grfKeyState, POINTL pt,DWORD *pdwEffect) { m_DropType = QueryDataObject(pDataObject); *pdwEffect = DROPEFFECT_NONE; return S_OK; } HRESULT __stdcall CProjectDropTargetBase::DragOver(DWORD grfKeyState,POINTL pt,DWORD *pdwEffect) { if (m_DropType != DT_NONE && OnDragOver(pt)) *pdwEffect = m_DropType == DT_HDROP ? DROPEFFECT_COPY : DROPEFFECT_MOVE; else *pdwEffect = DROPEFFECT_NONE; return S_OK; } HRESULT __stdcall CProjectDropTargetBase::DragLeave() { OnDragLeave(); return S_OK; } HRESULT __stdcall CProjectDropTargetBase::Drop(IDataObject *pDataObject,DWORD grfKeyState, POINTL pt,DWORD *pdwEffect) { if (m_DropType != DT_NONE && OnDrop(pt,pDataObject)) *pdwEffect = m_DropType == DT_HDROP ? DROPEFFECT_COPY : DROPEFFECT_MOVE; else *pdwEffect = DROPEFFECT_NONE; return S_OK; } ================================================ FILE: src/app/project_drop_target_base.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once class CProjectDropTargetBase : public IDropTarget { protected: // Custom InfraRecorder clip board format identifier. unsigned int m_uiClipFormat; private: enum eDropType { DT_NONE, DT_HDROP, DT_IRPROJECT }; eDropType m_DropType; long m_lRefCount; eDropType QueryDataObject(IDataObject *pDataObject); public: CProjectDropTargetBase(); ~CProjectDropTargetBase(); // IUnknown implementation. HRESULT __stdcall QueryInterface(REFIID iid,void **ppvObject); ULONG __stdcall AddRef(); ULONG __stdcall Release(); // IDropTarget implementation. HRESULT __stdcall DragEnter(IDataObject *pDataObject,DWORD grfKeyState,POINTL pt,DWORD *pdwEffect); HRESULT __stdcall DragOver(DWORD grfKeyState,POINTL pt,DWORD *pdwEffect); HRESULT __stdcall DragLeave(); HRESULT __stdcall Drop(IDataObject *pDataObject,DWORD grfKeyState,POINTL pt,DWORD *pdwEffect); // To be implemented by inheritor. virtual bool OnDragOver(POINTL ptCursor) = 0; virtual bool OnDrop(POINTL ptCursor,IDataObject *pDataObject) = 0; virtual void OnDragLeave() = 0; }; ================================================ FILE: src/app/project_manager.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include #include #include #include #include "string_table.hh" #include "main_frm.hh" #include "audio_util.hh" #include "settings.hh" #include "cd_text.hh" #include "lang_util.hh" #include "infrarecorder.hh" #include "project_manager.hh" CProjectManager g_ProjectManager; CProjectManager::CFileTransaction::CFileTransaction(eMode Mode) : m_Mode(Mode) { } CProjectManager::CFileTransaction::~CFileTransaction() { } bool CProjectManager::CFileTransaction::AddDataFile(CProjectNode *pParentNode,const TCHAR *szFileName, const TCHAR *szFilePath,const TCHAR *szFullPath, FILETIME *pFileTime,unsigned __int64 uiSize) { // Make sure that a file with this name does not already exist. CItemData *pExistingItemData = g_TreeManager.GetChildItem(pParentNode,szFileName); if (pExistingItemData != NULL) { if (m_ReplaceDlg.Execute(szFullPath,pExistingItemData)) g_ProjectManager.RemoveFile(pParentNode,pExistingItemData); else return false; } // Add the new item. CItemData *pItemData = new CItemData(); if (m_Mode == MODE_IMPORT) pItemData->ucFlags |= PROJECTITEM_FLAG_ISIMPORTED | PROJECTITEM_FLAG_ISLOCKED; // Paths. pItemData->SetFileName(szFileName); pItemData->SetFilePath(szFilePath); lstrcpy(pItemData->szFullPath,szFullPath); // File type. SHFILEINFO shFileInfo; if (SHGetFileInfo(szFileName,FILE_ATTRIBUTE_NORMAL,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_TYPENAME)) { lstrcpy(pItemData->szFileType,shFileInfo.szTypeName); } // File time. FILETIME LocalFileTime; if (FileTimeToLocalFileTime(pFileTime,&LocalFileTime) == TRUE) FileTimeToDosDateTime(&LocalFileTime,&pItemData->usFileDate,&pItemData->usFileTime); // File size. pItemData->uiSize = uiSize; pParentNode->m_Files.push_back(pItemData); // Increase the total length counter. g_ProjectManager.m_pSpaceMeter->IncreaseAllocatedSize(pItemData->uiSize); return true; } CItemData *CProjectManager::CFileTransaction:: AddDataFile(CProjectNode *pParentNode,const TCHAR *szFullPath) { // Make sure that a file with this name does not already exist. TCHAR szFileName[MAX_PATH]; lstrcpy(szFileName,szFullPath); ExtractFileName(szFileName); CItemData *pExistingItemData = g_TreeManager.GetChildItem(pParentNode,szFileName); if (pExistingItemData != NULL) { if (m_ReplaceDlg.Execute(szFullPath,pExistingItemData)) g_ProjectManager.RemoveFile(pParentNode,pExistingItemData); else return false; } // Add the new item. CItemData *pItemData = new CItemData(); if (m_Mode == MODE_IMPORT) pItemData->ucFlags |= PROJECTITEM_FLAG_ISIMPORTED | PROJECTITEM_FLAG_ISLOCKED; // Paths. pItemData->SetFileName(szFileName); TCHAR *szSafeFilePath = pItemData->BeginEditFilePath(); lstrcpy(szSafeFilePath,pParentNode->pItemData->GetFilePath()); lstrcat(szSafeFilePath,pParentNode->pItemData->GetFileName()); lstrcat(szSafeFilePath,_T("/")); pItemData->EndEditFilePath(); lstrcpy(pItemData->szFullPath,szFullPath); // File type. SHFILEINFO shFileInfo; if (SHGetFileInfo(szFullPath,FILE_ATTRIBUTE_NORMAL,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_TYPENAME)) { lstrcpy(pItemData->szFileType,shFileInfo.szTypeName); } // File time. struct tm AccessTime,ModifyTime,CreateTime; ckcore::File::time(szFullPath,AccessTime,ModifyTime,CreateTime); ckcore::convert::tm_to_dostime(ModifyTime,pItemData->usFileDate,pItemData->usFileTime); // File size. pItemData->uiSize = ckcore::File::size(szFullPath); pParentNode->m_Files.push_back(pItemData); // Increase the total length counter. g_ProjectManager.m_pSpaceMeter->IncreaseAllocatedSize(pItemData->uiSize); return pItemData; } CProjectNode *CProjectManager::CFileTransaction:: AddFolder(CProjectNode *pParentNode,const TCHAR *szFolderName, const TCHAR *szFolderPath,const TCHAR *szFullPath, FILETIME *pFileTime) { // Make sure that this folder does not already exist. CProjectNode *pExistingNode = g_TreeManager.GetChildNode(pParentNode,szFolderName); if (pExistingNode != NULL) return pExistingNode; // Add a new node. CProjectNode *pNode = new CProjectNode(pParentNode); if (m_Mode == MODE_IMPORT) pNode->pItemData->ucFlags |= PROJECTITEM_FLAG_ISIMPORTED | PROJECTITEM_FLAG_ISLOCKED; // Paths. pNode->pItemData->SetFileName(szFolderName); pNode->pItemData->SetFilePath(szFolderPath); lstrcpy(pNode->pItemData->szFullPath,szFullPath); // File type. SHFILEINFO shFileInfo; if (SHGetFileInfo(_T(""),FILE_ATTRIBUTE_DIRECTORY,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_TYPENAME)) { lstrcpy(pNode->pItemData->szFileType,shFileInfo.szTypeName); } else { lstrcpy(pNode->pItemData->szFileType,_T("")); } // File time. FILETIME LocalFileTime; if (FileTimeToLocalFileTime(pFileTime,&LocalFileTime) == TRUE) FileTimeToDosDateTime(&LocalFileTime,&pNode->pItemData->usFileDate,&pNode->pItemData->usFileTime); pParentNode->m_Children.push_back(pNode); g_TreeManager.AddTreeNode(pParentNode->m_hTreeItem,pNode); return pNode; } CProjectNode *CProjectManager::CFileTransaction:: AddFolder(CProjectNode *pParentNode,const TCHAR *szFullPath) { // Make sure that this folder does not already exist. TCHAR szFolderName[MAX_PATH]; lstrcpy(szFolderName,szFullPath); ExtractFileName(szFolderName); CProjectNode *pExistingNode = g_TreeManager.GetChildNode(pParentNode,szFolderName); if (pExistingNode != NULL) return pExistingNode; // Add a new node. CProjectNode *pNode = new CProjectNode(pParentNode); if (m_Mode == MODE_IMPORT) pNode->pItemData->ucFlags |= PROJECTITEM_FLAG_ISIMPORTED | PROJECTITEM_FLAG_ISLOCKED; // Paths. pNode->pItemData->SetFileName(szFolderName); TCHAR *szSafeFilePath = pNode->pItemData->BeginEditFilePath(); lstrcpy(szSafeFilePath,pParentNode->pItemData->GetFilePath()); lstrcat(szSafeFilePath,pParentNode->pItemData->GetFileName()); lstrcat(szSafeFilePath,_T("/")); pNode->pItemData->EndEditFilePath(); lstrcpy(pNode->pItemData->szFullPath,szFullPath); // File type. SHFILEINFO shFileInfo; if (SHGetFileInfo(_T(""),FILE_ATTRIBUTE_DIRECTORY,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_TYPENAME)) { lstrcpy(pNode->pItemData->szFileType,shFileInfo.szTypeName); } else { lstrcpy(pNode->pItemData->szFileType,_T("")); } // Directory time. struct tm AccessTime,ModifyTime,CreateTime; ckcore::Directory::time(szFullPath,AccessTime,ModifyTime,CreateTime); ckcore::convert::tm_to_dostime(ModifyTime,pNode->pItemData->usFileDate, pNode->pItemData->usFileTime); pParentNode->m_Children.push_back(pNode); g_TreeManager.AddTreeNode(pParentNode->m_hTreeItem,pNode); return pNode; } bool CProjectManager::CFileTransaction:: AddAudioFile(CProjectNode *pParentNode,const TCHAR *szFullPath) { // Check if M3U play list, in that case import the contents from it. ckcore::Path FullPath(szFullPath); if (!ckcore::string::astrcmpi(FullPath.ext_name().c_str(),ckT("m3u"))) return g_ProjectManager.Import(szFullPath); bool bEncoded = false; unsigned __int64 uiDuration = 0; // If the audio file is not a Wave file, try to find a codec that can handle it. if (GetAudioFormat(szFullPath) != AUDIOFORMAT_WAVE) { // Audio file information. int iNumChannels = -1; int iSampleRate = -1; int iBitRate = -1; for (unsigned int i = 0; i < g_CodecManager.m_Codecs.size(); i++) { // We're only interested in decoders. if ((g_CodecManager.m_Codecs[i]->irc_capabilities() & IRC_HAS_DECODER) == 0) continue; if (g_CodecManager.m_Codecs[i]->irc_decode_init(szFullPath,iNumChannels, iSampleRate,iBitRate,uiDuration)) { // Exit the decoder immediately since we don't want to decode the file yet. g_CodecManager.m_Codecs[i]->irc_decode_exit(); bEncoded = true; break; } } if (!bEncoded) { lngMessageBox(*g_pMainFrame,FAILURE_UNSUPAUDIO,GENERAL_ERROR,MB_OK | MB_ICONERROR); return false; } } CItemData *pItemData = new CItemData(); if (m_Mode == MODE_IMPORT) pItemData->ucFlags |= PROJECTITEM_FLAG_ISIMPORTED | PROJECTITEM_FLAG_ISLOCKED; // Paths. TCHAR *szSafeFileName = pItemData->BeginEditFileName(); lstrcpy(szSafeFileName,szFullPath); ExtractFileName(szSafeFileName); pItemData->EndEditFileName(); TCHAR *szSafeFilePath = pItemData->BeginEditFilePath(); lstrcpy(szSafeFilePath,pParentNode->pItemData->GetFilePath()); lstrcat(szSafeFilePath,pParentNode->pItemData->GetFileName()); lstrcat(szSafeFilePath,_T("/")); pItemData->EndEditFilePath(); lstrcpy(pItemData->szFullPath,szFullPath); // Track length. if (bEncoded) pItemData->GetAudioData()->uiTrackLength = uiDuration; else pItemData->GetAudioData()->uiTrackLength = GetAudioLength(szFullPath); if (g_ProjectManager.m_iProjectType == PROJECTTYPE_MIXED) // Count using the Mode-1 sector size since the spacemeter in these projects are based on that disc size. pItemData->uiSize = (pItemData->GetAudioData()->uiTrackLength / 1000) * 75 * 2048; else pItemData->uiSize = pItemData->GetAudioData()->uiTrackLength; pParentNode->m_Files.push_back(pItemData); // Increase the total length counter. g_ProjectManager.m_pSpaceMeter->IncreaseAllocatedSize(pItemData->uiSize); return true; } void CProjectManager::CFileTransaction::AddFilesInFolder(CProjectNode *pParentNode, std::vector &FolderStack) { // Real parent path. TCHAR szRealParentPath[MAX_PATH]; lstrcpy(szRealParentPath,pParentNode->pItemData->szFullPath); IncludeTrailingBackslash(szRealParentPath); // Search path. TCHAR szSearchPath[MAX_PATH]; lstrcpy(szSearchPath,szRealParentPath); lstrcat(szSearchPath,TEXT("*")); // Internal parent path. TCHAR szParentPath[MAX_PATH]; lstrcpy(szParentPath,pParentNode->pItemData->GetFilePath()); lstrcat(szParentPath,pParentNode->pItemData->GetFileName()); lstrcat(szParentPath,_T("/")); WIN32_FIND_DATA FileData; HANDLE hFind = FindFirstFile(szSearchPath,&FileData); if (hFind != INVALID_HANDLE_VALUE) { if (lstrcmp(FileData.cFileName,TEXT(".")) && lstrcmp(FileData.cFileName,TEXT(".."))) { if (FileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) { TCHAR szFullName[MAX_PATH]; lstrcpy(szFullName,szRealParentPath); lstrcat(szFullName,FileData.cFileName); FolderStack.push_back(AddFolder(pParentNode,FileData.cFileName,szParentPath,szFullName,&FileData.ftLastWriteTime)); } else { TCHAR szFullName[MAX_PATH]; lstrcpy(szFullName,szRealParentPath); lstrcat(szFullName,FileData.cFileName); unsigned __int64 uiFileSize = 0; if (FileData.nFileSizeHigh == 0) uiFileSize = FileData.nFileSizeLow; else uiFileSize = ((unsigned __int64)FileData.nFileSizeHigh << 32) | FileData.nFileSizeLow; AddDataFile(pParentNode,FileData.cFileName,szParentPath,szFullName,&FileData.ftLastWriteTime,uiFileSize); } } while (FindNextFile(hFind,&FileData) != 0) { if (lstrcmp(FileData.cFileName,TEXT(".")) && lstrcmp(FileData.cFileName,TEXT(".."))) { if (FileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) { TCHAR szFullName[MAX_PATH]; lstrcpy(szFullName,szRealParentPath); lstrcat(szFullName,FileData.cFileName); FolderStack.push_back(AddFolder(pParentNode,FileData.cFileName,szParentPath,szFullName,&FileData.ftLastWriteTime)); } else { TCHAR szFullName[MAX_PATH]; lstrcpy(szFullName,szRealParentPath); lstrcat(szFullName,FileData.cFileName); unsigned __int64 uiFileSize = 0; if (FileData.nFileSizeHigh == 0) uiFileSize = FileData.nFileSizeLow; else uiFileSize = ((unsigned __int64)FileData.nFileSizeHigh << 32) | FileData.nFileSizeLow; AddDataFile(pParentNode,FileData.cFileName,szParentPath,szFullName,&FileData.ftLastWriteTime,uiFileSize); } } } } FindClose(hFind); } /** Adds the specified file to specifed node. If pTargetNode is NULL then the file will be added to the current folder (node) in the project view. @param szFullPath the absolute path to a file on the file system. @param pTargetNode the node that the file should be added to. @return true if successfull, otherwise false. */ bool CProjectManager::CFileTransaction:: AddFile(const TCHAR *szFullPath,CProjectNode *pTargetNode) { // Check if we're realing with a folder. if (ckcore::Directory::exist(szFullPath)) { // We can't add folder to an audio disc. if (g_ProjectManager.m_iViewType != PROJECTVIEWTYPE_DATA) { lngMessageBox(*g_pMainFrame,ERROR_AUDIOADDFOLDER,GENERAL_ERROR,MB_OK | MB_ICONERROR); return false; } // Add this folder. if (pTargetNode == NULL) pTargetNode = AddFolder(g_TreeManager.GetCurrentNode(),szFullPath); else pTargetNode = AddFolder(pTargetNode,szFullPath); std::vector FolderStack; AddFilesInFolder(pTargetNode,FolderStack); while (FolderStack.size() > 0) { pTargetNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); AddFilesInFolder(pTargetNode,FolderStack); } g_TreeManager.Refresh(); g_ProjectManager.m_pTreeView->Expand(g_TreeManager.GetRootNode()->m_hTreeItem); } else { if (pTargetNode == NULL) pTargetNode = g_TreeManager.GetCurrentNode(); if (g_ProjectManager.m_iViewType == PROJECTVIEWTYPE_DATA && pTargetNode != g_ProjectManager.m_pMixAudioNode) { AddDataFile(pTargetNode,szFullPath); } else { AddAudioFile(pTargetNode,szFullPath); } g_TreeManager.Refresh(); } g_ProjectManager.m_bModified = true; return true; } /** Adds the specified file to specifed path in the project. @param szFullPath the absolute path to a file on the file system. @param szProjectPath the target path in the project. @return If successfull, a pointer to the CItemData object of the new item. If unsuccessfull the function returns NULL. @see AddFile(const TCHAR *szFullPath,CProjectNode *pTargetNode) */ CItemData *CProjectManager::CFileTransaction:: AddFile(const TCHAR *szFullPath,const TCHAR *szProjectPath) { CProjectNode *pParent = g_TreeManager.AddPath(szProjectPath); if (pParent == NULL) return NULL; return AddDataFile(pParent,szFullPath); } /** Moves the specified item to the specified new parent node. @param pItemParent the current parent node of pItemData. @param pItemData the item to move. @param pNewParent the new node that pItemData should be moved to. @return true if successfull, otherwise false. */ bool CProjectManager::CFileTransaction:: MoveFile(CProjectNode *pItemParent,CItemData *pItemData,CProjectNode *pNewParent) { // We can only move files in data projects. if (g_ProjectManager.m_iViewType != PROJECTVIEWTYPE_DATA) return false; // Check if a file or folder already exists in the destination folder. CItemData *pExistingItemData = g_TreeManager.GetChildItem(pNewParent,pItemData->GetFileName()); if (pExistingItemData != NULL) { // It does not make sense to move oneself to itself. if (pExistingItemData == pItemData) return false; if (m_ReplaceDlg.Execute(pItemData,pExistingItemData)) g_ProjectManager.RemoveFile(pNewParent,pExistingItemData); else return false; } if (!g_TreeManager.MoveEntry(pItemParent,pItemData,pNewParent)) lngMessageBox(*g_pMainFrame,ERROR_MOVESAMESRCDST,GENERAL_ERROR,MB_OK | MB_ICONERROR); g_TreeManager.Refresh(); g_ProjectManager.m_bModified = true; return true; } /** Moves the specified item to the current folder (node) in the project view. @param pItemParent the current parent node of pItemData. @param pItemData the item to move. @return true if successfull, otherwise false. @see MoveFile(CProjectNode *pItemParent,CItemData *pItemData,CProjectNode *pNewParent) */ bool CProjectManager::CFileTransaction:: MoveFileToCurrent(CProjectNode *pItemParent,CItemData *pItemData) { return MoveFile(pItemParent,pItemData,g_TreeManager.GetCurrentNode()); } CProjectManager::CProjectManager() { m_iProjectType = -1; m_iProjectMedia = -1; m_iViewType = -1; m_iActiveView = AV_TREE; m_pProjectView = NULL; m_pContainer = NULL; m_pSpaceMeter = NULL; m_pListView = NULL; m_pTreeView = NULL; } CProjectManager::~CProjectManager() { } LRESULT CProjectManager::OnNewFolder(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Make sure that this action is allowed to happen (accelerators does not care about menu item state). if (g_pMainFrame->UIGetState(ID_EDIT_NEWFOLDER) & g_pMainFrame->UPDUI_DISABLED) return 0; switch (m_iActiveView) { case AV_TREE: TreeAddNewFolder(m_pActionNode); break; case AV_LIST: ListAddNewFolder(); break; }; m_bModified = true; return 0; } LRESULT CProjectManager::OnRename(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Make sure that this action is allowed to happen (accelerators does not care about menu item state). if (g_pMainFrame->UIGetState(ID_EDIT_RENAME) & g_pMainFrame->UPDUI_DISABLED) return 0; switch (m_iActiveView) { case AV_TREE: // We can't rename locked items. if (!(m_pActionNode->pItemData->ucFlags & PROJECTITEM_FLAG_ISLOCKED)) m_pTreeView->EditLabel(m_pActionNode->m_hTreeItem); break; case AV_LIST: int iItemIndex = -1; iItemIndex = m_pListView->GetNextItem(iItemIndex,LVNI_SELECTED | LVNI_FOCUSED); // Make sure that atleast one item is selected with focus. if (iItemIndex == -1) break; CItemData *pItemData = (CItemData *)m_pListView->GetItemData(iItemIndex); if (!(pItemData->ucFlags & PROJECTITEM_FLAG_ISLOCKED)) m_pListView->EditLabel(iItemIndex); break; }; return 0; } LRESULT CProjectManager::OnRemove(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { // Make sure that this action is allowed to happen (accelerators does not care about menu item state). if (g_pMainFrame->UIGetState(ID_EDIT_REMOVE) & g_pMainFrame->UPDUI_DISABLED) return 0; // We need to store the current active view since it will change after the message box has been shown. int iActiveView = m_iActiveView; if (lngMessageBox(*g_pMainFrame,CONFIRM_REMOVEITEMS,GENERAL_QUESTION,MB_YESNO | MB_ICONQUESTION) != IDYES) return 0; switch (iActiveView) { case AV_TREE: TreeRemoveNode(m_pActionNode); break; case AV_LIST: ListRemoveSel(); break; }; m_iActiveView = iActiveView; m_bModified = true; return 0; } void CProjectManager::SetupDataListView() { m_iViewType = PROJECTVIEWTYPE_DATA; // Remove all columns. int iColCount = m_pListView->GetHeader().GetItemCount(); for (int i = 0; i < iColCount; i++) m_pListView->DeleteColumn(0); // Add the new columns. m_pListView->InsertColumn(0,lngGetString(COLUMN_NAME),LVCFMT_LEFT,250,COLUMN_SUBINDEX_NAME); m_pListView->InsertColumn(1,lngGetString(COLUMN_SIZE),LVCFMT_RIGHT,100,COLUMN_SUBINDEX_SIZE); m_pListView->InsertColumn(2,lngGetString(COLUMN_TYPE),LVCFMT_LEFT,180,COLUMN_SUBINDEX_TYPE); m_pListView->InsertColumn(3,lngGetString(COLUMN_MODIFIED),LVCFMT_LEFT,120,COLUMN_SUBINDEX_MODIFIED); m_pListView->InsertColumn(4,lngGetString(COLUMN_PATH),LVCFMT_LEFT,120,COLUMN_SUBINDEX_PATH); // Update menu items. EnableAll(ID_EDIT_NEWFOLDER,true,g_pMainFrame->m_hProjListNoSelMenu); EnableAll(ID_EDIT_RENAME,false,g_pMainFrame->m_hProjListSelMenu); EnableAll(ID_EDIT_REMOVE,false); // Enable editing of names. unsigned long ulViewStyle = m_pListView->GetWindowLong(GWL_STYLE); m_pListView->SetWindowLong(GWL_STYLE,ulViewStyle | LVS_EDITLABELS); // Specifiy the sort-column. SendMessage(m_pListView->GetHeader(),WM_CHC_SETSORTCOLUMN,0,0); } void CProjectManager::SetupAudioListView() { m_iViewType = PROJECTVIEWTYPE_AUDIO; // Remove all columns. int iColCount = m_pListView->GetHeader().GetItemCount(); for (int i = 0; i < iColCount; i++) m_pListView->DeleteColumn(0); // Add the new columns. m_pListView->InsertColumn(0,lngGetString(COLUMN_TRACK),LVCFMT_LEFT,45,COLUMN_SUBINDEX_TRACK); m_pListView->InsertColumn(1,lngGetString(COLUMN_TITLE),LVCFMT_LEFT,220,COLUMN_SUBINDEX_TITLE); m_pListView->InsertColumn(2,lngGetString(COLUMN_LENGTH),LVCFMT_LEFT,60,COLUMN_SUBINDEX_LENGTH); m_pListView->InsertColumn(3,lngGetString(COLUMN_LOCATION),LVCFMT_LEFT,450,COLUMN_SUBINDEX_LOCATION); // Update menu items. EnableAll(ID_EDIT_NEWFOLDER,false,g_pMainFrame->m_hProjListNoSelMenu); EnableAll(ID_EDIT_RENAME,false,g_pMainFrame->m_hProjListSelMenu); EnableAll(ID_EDIT_REMOVE,false); // Disable editing of names. unsigned long ulViewStyle = m_pListView->GetWindowLong(GWL_STYLE); m_pListView->SetWindowLong(GWL_STYLE,ulViewStyle & ~LVS_EDITLABELS); // Specifiy the sort-column. SendMessage(m_pListView->GetHeader(),WM_CHC_SETSORTCOLUMN,1,0); } /** Assigns graphical controls to the project manage so that they will be properly updated when the project changes. @param pProjectView project splitter view control. @param pContainer project list view container control. @param pSpaceMeter space meter control. @param pListView project list view control. @param pTreeView project tree view control. */ void CProjectManager::AssignControls(CSplitterWindow *pProjectView,CCustomContainer *pContainer, CSpaceMeter *pSpaceMeter,CListViewCtrl *pListView, CTreeViewCtrlEx *pTreeView) { m_pProjectView = pProjectView; m_pContainer = pContainer; m_pSpaceMeter = pSpaceMeter; m_pListView = pListView; m_pTreeView = pTreeView; } /** Creates a new empty data project. @param bDVD specifies whether the project should be recorded to DVD media or not. */ void CProjectManager::NewDataProject(int iDiscMedia) { // Reset the old project settings. g_ProjectSettings.Reset(); m_bModified = false; if (m_pProjectView != NULL) m_pProjectView->SetSinglePaneMode(SPLIT_PANE_NONE); CloseProject(); m_iProjectType = PROJECTTYPE_DATA; m_iProjectMedia = iDiscMedia; if (m_pProjectView != NULL) SetupDataListView(); // Get system date and time. SYSTEMTIME st; GetLocalTime(&st); TCHAR szDate[8]; GetDateFormat(LOCALE_USER_DEFAULT,0,&st,_T("yyMMdd_"),szDate,8); TCHAR szDateTime[12]; lsprintf(szDateTime,_T("%s%.2d%.2d"),szDate,st.wHour,st.wMinute); // Insert tree root item. g_TreeManager.CreateTree(szDateTime,PROJECTTREE_IMAGEINDEX_DATA); // Update the space meter. if (m_pSpaceMeter != NULL) { m_pSpaceMeter->SetDisplayMode(PROJECTVIEWTYPE_DATA); m_pSpaceMeter->SetDiscSize(m_iProjectMedia); m_pSpaceMeter->SetAllocatedSize(0); } // Project settings. lstrcpy(g_ProjectSettings.m_szLabel,szDateTime); // Enable/disable menu items. g_pMainFrame->UIEnable(ID_BURNCOMPILATION_DISCIMAGE,true); g_pMainFrame->UIEnable(ID_ACTIONS_IMPORTSESSION,true); } /** Creates a mew empty audio project. */ void CProjectManager::NewAudioProject(int iDiscMedia) { // Reset the old project settings. g_ProjectSettings.Reset(); m_bModified = false; if (m_pProjectView != NULL) m_pProjectView->SetSinglePaneMode(SPLIT_PANE_RIGHT); CloseProject(); m_iProjectType = PROJECTTYPE_AUDIO; m_iProjectMedia = iDiscMedia; if (m_pListView != NULL) SetupAudioListView(); // Insert tree root item. g_TreeManager.CreateTree(lngGetString(PROJECT_AUDIO),PROJECTTREE_IMAGEINDEX_AUDIO); // Update the space meter. if (m_pSpaceMeter != NULL) { m_pSpaceMeter->SetDisplayMode(PROJECTVIEWTYPE_AUDIO); m_pSpaceMeter->SetDiscSize(m_iProjectMedia); m_pSpaceMeter->SetAllocatedSize(0); } // Project settings. g_ProjectSettings.m_szLabel[0] = '\0'; // Enable/disable menu items. g_pMainFrame->UIEnable(ID_BURNCOMPILATION_DISCIMAGE,false); g_pMainFrame->UIEnable(ID_ACTIONS_IMPORTSESSION,false); } /** Creates a new empty mixed mode project. */ void CProjectManager::NewMixedProject(int iDiscMedia) { // Reset the old project settings. g_ProjectSettings.Reset(); m_bModified = false; if (m_pProjectView != NULL) m_pProjectView->SetSinglePaneMode(SPLIT_PANE_NONE); CloseProject(); m_iProjectType = PROJECTTYPE_MIXED; m_iProjectMedia = iDiscMedia; // By default we display the data view. if (m_pListView != NULL) SetupDataListView(); // Insert tree root item. g_TreeManager.CreateTree(lngGetString(PROJECT_MIXED),PROJECTTREE_IMAGEINDEX_MIXED); // Get system date and time. SYSTEMTIME st; GetLocalTime(&st); TCHAR szDate[8]; GetDateFormat(LOCALE_USER_DEFAULT,0,&st,_T("yyMMdd_"),szDate,8); TCHAR szDateTime[12]; lsprintf(szDateTime,_T("%s%.2d%.2d"),szDate,st.wHour,st.wMinute); m_pMixDataNode = g_TreeManager.InsertVirtualRoot(szDateTime,PROJECTTREE_IMAGEINDEX_DATA); m_pMixAudioNode = g_TreeManager.InsertVirtualRoot(lngGetString(PROJECT_AUDIO),PROJECTTREE_IMAGEINDEX_AUDIO); if (m_pTreeView != NULL) m_pTreeView->Select(m_pMixDataNode->m_hTreeItem,TVGN_CARET); // Update the space meter. if (m_pSpaceMeter != NULL) { m_pSpaceMeter->SetDisplayMode(PROJECTVIEWTYPE_DATA); m_pSpaceMeter->SetDiscSize(m_iProjectMedia); m_pSpaceMeter->SetAllocatedSize(0); } // Project settings. lstrcpy(g_ProjectSettings.m_szLabel,szDateTime); // Enable/disable menu items. g_pMainFrame->UIEnable(ID_BURNCOMPILATION_DISCIMAGE,true); g_pMainFrame->UIEnable(ID_ACTIONS_IMPORTSESSION,false); } /** Changes to project data view for mixed mode projects. */ void CProjectManager::DataSelected() { if (m_iProjectType != PROJECTTYPE_MIXED) return; SetupDataListView(); } /** Changes to project audio view for mixed mode projects. */ void CProjectManager::AudioSelected() { if (m_iProjectType != PROJECTTYPE_MIXED) return; SetupAudioListView(); } /** Generates a new sub folder name for the specified parent node. For example if a folder named "New Folder" already exists in that parent, the new one should be nameed "New Folder (2)" (unless that one already exists). @param pParent parent node that the new folder should be created in. @param szFolderName the output string that should hold the generated folder name. @param uiFolderNameSize the size of the szFolderName variable (in TCHARs). @return true if successfull, false otherwise. */ bool CProjectManager::GenerateNewFolderName(CProjectNode *pParent,TCHAR *szFolderName, unsigned int uiFolderNameSize) { if (g_TreeManager.GetChildItem(pParent,lngGetString(MISC_NEWFOLDER)) != NULL) { TCHAR szFolderNamePattern[64]; size_t iMaxLen = sizeof(szFolderNamePattern) - (1 + 10 + 3); if ((size_t)lstrlen(lngGetString(MISC_NEWFOLDER)) > iMaxLen) lstrncpy(szFolderNamePattern,lngGetString(MISC_NEWFOLDER),iMaxLen); else lstrcpy(szFolderNamePattern,lngGetString(MISC_NEWFOLDER)); lstrcat(szFolderNamePattern,_T(" (%u)")); for (unsigned int i = 2; i < 0xFFFFFFFF; i++) { lsprintf(szFolderName,szFolderNamePattern,i); if (!g_TreeManager.GetChildItem(pParent,szFolderName) != NULL) return true; } return false; } else { if ((unsigned int)lstrlen(lngGetString(MISC_NEWFOLDER)) >= uiFolderNameSize) lstrncpy(szFolderName,lngGetString(MISC_NEWFOLDER),uiFolderNameSize - 1); else lstrcpy(szFolderName,lngGetString(MISC_NEWFOLDER)); } return true; } /** Adds a new empty folder to the current folder (node) in the project through the project list view. */ bool CProjectManager::ListAddNewFolder() { CProjectNode *pCurNode = g_TreeManager.GetCurrentNode(); TCHAR szFolderName[64]; if (!GenerateNewFolderName(pCurNode,szFolderName,sizeof(szFolderName))) return false; // Create the new node. CProjectNode *pNode = new CProjectNode(pCurNode); // Paths. pNode->pItemData->SetFileName(szFolderName); TCHAR *szSafeFilePath = pNode->pItemData->BeginEditFilePath(); g_TreeManager.GetCurrentPath(szSafeFilePath); pNode->pItemData->EndEditFilePath(); // File type. SHFILEINFO shFileInfo; if (SHGetFileInfo(_T(""),FILE_ATTRIBUTE_DIRECTORY,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_TYPENAME)) { lstrcpy(pNode->pItemData->szFileType,shFileInfo.szTypeName); } else { lstrcpy(pNode->pItemData->szFileType,_T("")); } // File time. SYSTEMTIME SystemTime; GetLocalTime(&SystemTime); FILETIME FileTime; SystemTimeToFileTime(&SystemTime,&FileTime); FileTimeToDosDateTime(&FileTime,&pNode->pItemData->usFileDate,&pNode->pItemData->usFileTime); // Add the new node as a child to the current. pCurNode->m_Children.push_back(pNode); g_TreeManager.AddTreeNode(pCurNode->m_hTreeItem,pNode); g_TreeManager.Refresh(); m_pTreeView->Expand(pCurNode->m_hTreeItem); return true; } /** Adds a new empty folder to the current folder (node) in the project through the project tree view. */ bool CProjectManager::TreeAddNewFolder(CProjectNode *pParentNode) { TCHAR szFolderName[64]; if (!GenerateNewFolderName(pParentNode,szFolderName,sizeof(szFolderName))) return false; // Create the new node. CProjectNode *pNode = new CProjectNode(pParentNode); // Paths. pNode->pItemData->SetFileName(szFolderName); TCHAR *szSafeFilePath = pNode->pItemData->BeginEditFilePath(); lstrcpy(szSafeFilePath,pParentNode->pItemData->GetFilePath()); lstrcat(szSafeFilePath,pParentNode->pItemData->GetFileName()); lstrcat(szSafeFilePath,_T("/")); pNode->pItemData->EndEditFilePath(); // File type. SHFILEINFO shFileInfo; if (SHGetFileInfo(_T(""),FILE_ATTRIBUTE_DIRECTORY,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_TYPENAME)) { lstrcpy(pNode->pItemData->szFileType,shFileInfo.szTypeName); } else { lstrcpy(pNode->pItemData->szFileType,_T("")); } // File time. SYSTEMTIME SystemTime; GetLocalTime(&SystemTime); FILETIME FileTime; SystemTimeToFileTime(&SystemTime,&FileTime); FileTimeToDosDateTime(&FileTime,&pNode->pItemData->usFileDate,&pNode->pItemData->usFileTime); pParentNode->m_Children.push_back(pNode); g_TreeManager.AddTreeNode(pParentNode->m_hTreeItem,pNode); g_TreeManager.Refresh(); m_pTreeView->Expand(pParentNode->m_hTreeItem); return true; } /** Removes the specified file from the specified parent folder (node). @param pParentNode parent of the folder file to be removed from the project. @param pItemData item that should be removed. */ void CProjectManager::RemoveFile(CProjectNode *pParentNode,CItemData *pItemData) { // Update the space meter. m_pSpaceMeter->DecreaseAllocatedSize(pItemData->uiSize); // Remove the items. g_TreeManager.RemoveEntry(pParentNode,pItemData); } /** Removes the selected files and folders (in the list view) from the project. */ void CProjectManager::ListRemoveSel() { int iItemIndex = -1; iItemIndex = m_pListView->GetNextItem(iItemIndex,LVNI_SELECTED); while (iItemIndex != -1) { CItemData *pItemData = (CItemData *)m_pListView->GetItemData(iItemIndex); // If the item is locked, skip it. if (pItemData->ucFlags & PROJECTITEM_FLAG_ISLOCKED) { iItemIndex = m_pListView->GetNextItem(iItemIndex,LVNI_SELECTED); continue; } // Update the space meter. if (pItemData->ucFlags & PROJECTITEM_FLAG_ISFOLDER) m_pSpaceMeter->DecreaseAllocatedSize(g_TreeManager.GetNodeSize(g_TreeManager.GetCurrentNode(),pItemData)); else m_pSpaceMeter->DecreaseAllocatedSize(pItemData->uiSize); // Remove the items. g_TreeManager.RemoveEntry(g_TreeManager.GetCurrentNode(),pItemData); iItemIndex = m_pListView->GetNextItem(iItemIndex,LVNI_SELECTED); } g_TreeManager.Refresh(); } /** Removes the selected folder (in the tree view) from the project. */ void CProjectManager::TreeRemoveNode(CProjectNode *pNode) { // It's not possible to remove locked items. if (pNode->pItemData->ucFlags & PROJECTITEM_FLAG_ISLOCKED) return; // Update the space meter. m_pSpaceMeter->DecreaseAllocatedSize(g_TreeManager.GetNodeSize(pNode)); // Remove the node. g_TreeManager.RemoveEntry(pNode); g_TreeManager.Refresh(); NotifyTreeSelChanged((CProjectNode *)m_pTreeView->GetSelectedItem().GetData()); } /** Used for notifying the project manager that the list view selection has changed. @param uiSelCount new number of selected item in the list view. */ void CProjectManager::NotifyListSelChanged(unsigned int uiSelCount) { if (m_iViewType == PROJECTVIEWTYPE_DATA) { if (uiSelCount > 0) { EnableAll(ID_EDIT_RENAME,true,g_pMainFrame->m_hProjListSelMenu); EnableAll(ID_EDIT_REMOVE,true,g_pMainFrame->m_hProjListSelMenu); } else { EnableAll(ID_EDIT_RENAME,false,g_pMainFrame->m_hProjListSelMenu); EnableAll(ID_EDIT_REMOVE,false,g_pMainFrame->m_hProjListSelMenu); } } else if (m_iViewType == PROJECTVIEWTYPE_AUDIO) { if (uiSelCount > 0) EnableAll(ID_EDIT_REMOVE,true,g_pMainFrame->m_hProjListSelMenu); else EnableAll(ID_EDIT_REMOVE,false,g_pMainFrame->m_hProjListSelMenu); } // Currently the properties menu item only works when right-clicking on the project tree root. g_ProjectManager.EnableAll(ID_POPUPMENU_PROPERTIES,false,g_pMainFrame->m_hProjListSelMenu); } /** Used for notifying the project manager that the tree view selection has changed. @param pNode new selected node. */ void CProjectManager::NotifyTreeSelChanged(CProjectNode *pNode) { if (m_iProjectType == PROJECTTYPE_DATA) { g_ProjectManager.EnableAll(ID_EDIT_RENAME,true,g_pMainFrame->m_hProjListSelMenu); g_ProjectManager.EnableAll(ID_EDIT_REMOVE,pNode != g_TreeManager.GetRootNode(),g_pMainFrame->m_hProjListSelMenu); } else if (m_iProjectType == PROJECTTYPE_MIXED) { if (pNode == m_pMixAudioNode) { g_ProjectManager.EnableAll(ID_EDIT_RENAME,false,g_pMainFrame->m_hProjListSelMenu); g_ProjectManager.EnableAll(ID_EDIT_REMOVE,false,g_pMainFrame->m_hProjListSelMenu); } else { g_ProjectManager.EnableAll(ID_EDIT_RENAME,true,g_pMainFrame->m_hProjListSelMenu); g_ProjectManager.EnableAll(ID_EDIT_REMOVE,pNode != m_pMixDataNode,g_pMainFrame->m_hProjListSelMenu); } } // Currently the properties menu item only works when right-clicking on the project tree root. if (pNode == g_TreeManager.GetRootNode()) g_ProjectManager.EnableAll(ID_POPUPMENU_PROPERTIES,true,g_pMainFrame->m_hProjListSelMenu); else g_ProjectManager.EnableAll(ID_POPUPMENU_PROPERTIES,false,g_pMainFrame->m_hProjListSelMenu); } /** Sets the current active (selected) tree node. @param pNode the new node that should be treated as active. */ void CProjectManager::TreeSetActionNode(CProjectNode *pNode) { m_pActionNode = pNode; } /** Used for notifying the project manager that the project tree view has been activated and now has focus. */ void CProjectManager::TreeSetActive() { m_iActiveView = AV_TREE; } /** Used for notifying the project manager that the project list view has been activated and now has focus. */ void CProjectManager::ListSetActive() { m_iActiveView = AV_LIST; } /** Deletes all items imported from multisession discs from the project. */ void CProjectManager::DeleteImportedItems() { switch (m_iProjectType) { case PROJECTTYPE_DATA: g_TreeManager.DeleteImportedItems(g_TreeManager.GetRootNode()); break; }; g_TreeManager.Refresh(); } /** Closes the project. */ void CProjectManager::CloseProject() { m_iActiveView = AV_TREE; // Remove all items from the list and tree view. if (m_pTreeView != NULL) m_pTreeView->DeleteAllItems(); if (m_pListView != NULL) m_pListView->DeleteAllItems(); g_TreeManager.DestroyTree(); } void CProjectManager::EnableAll(int iID,bool bEnable,HMENU hMenu) { g_pMainFrame->UIEnable(iID,bEnable); m_pContainer->EnableToolbarButton(iID,bEnable); if (hMenu != NULL) ::EnableMenuItem(hMenu,iID,bEnable ? MF_ENABLED : MF_GRAYED); } /** Returns the current view type. @return the current view type. */ int CProjectManager::GetViewType() { return m_iViewType; } /** Returns the current project type. @return the current project type. */ int CProjectManager::GetProjectType() { return m_iProjectType; } /** Saves the current project to the specified Xml structure. @param pXml the Xml container which the project should be saved to. */ void CProjectManager::SaveProjectData(CXmlProcessor *pXml) { m_bModified = false; switch (m_iProjectType) { case PROJECTTYPE_DATA: pXml->AddElement(_T("Data"),_T(""),true); g_TreeManager.SaveNodeFileData(pXml,g_TreeManager.GetRootNode()); pXml->LeaveElement(); break; case PROJECTTYPE_AUDIO: pXml->AddElement(_T("Audio"),_T(""),true); g_TreeManager.SaveNodeAudioData(pXml,g_TreeManager.GetRootNode()); pXml->LeaveElement(); break; case PROJECTTYPE_MIXED: pXml->AddElement(_T("Data"),_T(""),true); g_TreeManager.SaveNodeFileData(pXml,m_pMixDataNode); pXml->LeaveElement(); pXml->AddElement(_T("Audio"),_T(""),true); g_TreeManager.SaveNodeAudioData(pXml,m_pMixAudioNode); pXml->LeaveElement(); break; }; } /** Loads the project from the specified Xml structure. @param pXml the Xml container which the project should be loaded from. @return true if the project was successfylly loaded, false otherwise. */ bool CProjectManager::LoadProjectData(CXmlProcessor *pXml) { switch (m_iProjectType) { case PROJECTTYPE_DATA: if (!pXml->EnterElement(_T("Data"))) return true; g_TreeManager.LoadNodeFileData(pXml,g_TreeManager.GetRootNode()); pXml->LeaveElement(); break; case PROJECTTYPE_AUDIO: if (!pXml->EnterElement(_T("Audio"))) return true; g_TreeManager.LoadNodeAudioData(pXml,g_TreeManager.GetRootNode(),PROJECTTYPE_AUDIO); pXml->LeaveElement(); break; case PROJECTTYPE_MIXED: if (!pXml->EnterElement(_T("Data"))) return true; g_TreeManager.LoadNodeFileData(pXml,m_pMixDataNode); pXml->LeaveElement(); if (!pXml->EnterElement(_T("Audio"))) return true; g_TreeManager.LoadNodeAudioData(pXml,m_pMixAudioNode,PROJECTTYPE_MIXED); pXml->LeaveElement(); break; }; return true; } void CProjectManager::SaveProjectFileSys(CXmlProcessor *pXml) { pXml->AddElement(_T("FileSystem"),_T(""),true); pXml->AddElement(_T("Identifier"),g_ProjectSettings.m_iFileSystem); pXml->LeaveElement(); } bool CProjectManager::LoadProjectFileSys(CXmlProcessor *pXml) { if (!pXml->EnterElement(_T("FileSystem"))) return false; pXml->GetSafeElementData(_T("Identifier"),&g_ProjectSettings.m_iFileSystem); pXml->LeaveElement(); return true; } void CProjectManager::SaveProjectISO(CXmlProcessor *pXml) { pXml->AddElement(_T("ISO"),_T(""),true); pXml->AddElement(_T("Level"),g_ProjectSettings.m_iIsoLevel); pXml->AddElement(_T("Format"),g_ProjectSettings.m_iIsoFormat); pXml->AddElement(_T("CharSet"),g_ProjectSettings.m_IsoCharSet); pXml->AddElement(_T("DeepDirs"),g_ProjectSettings.m_bDeepDirs); pXml->AddElement(_T("Joliet"),_T(""),true); pXml->AddElementAttr(_T("enable"),g_ProjectSettings.m_bJoliet); pXml->AddElement(_T("LongNames"),g_ProjectSettings.m_bJolietLongNames); pXml->LeaveElement(); pXml->AddElement(_T("OmitVerNum"),g_ProjectSettings.m_bOmitVerNum); pXml->LeaveElement(); } bool CProjectManager::LoadProjectISO(CXmlProcessor *pXml) { if (!pXml->EnterElement(_T("ISO"))) return false; pXml->GetSafeElementData(_T("Level"),&g_ProjectSettings.m_iIsoLevel); pXml->GetSafeElementData(_T("Format"),&g_ProjectSettings.m_iIsoFormat); int iCharSet = 0; pXml->GetSafeElementData(_T("CharSet"),&iCharSet); g_ProjectSettings.m_IsoCharSet = static_cast(iCharSet); pXml->GetSafeElementData(_T("DeepDirs"),&g_ProjectSettings.m_bDeepDirs); if (!pXml->EnterElement(_T("Joliet"))) { pXml->LeaveElement(); return false; } pXml->GetSafeElementAttrValue(_T("enable"),&g_ProjectSettings.m_bJoliet); pXml->GetSafeElementData(_T("LongNames"),&g_ProjectSettings.m_bJolietLongNames); pXml->LeaveElement(); pXml->GetSafeElementData(_T("OmitVerNum"),&g_ProjectSettings.m_bOmitVerNum); pXml->LeaveElement(); return true; } void CProjectManager::SaveProjectFields(CXmlProcessor *pXml) { pXml->AddElement(_T("Fields"),_T(""),true); pXml->AddElement(_T("Publisher"),g_ProjectSettings.m_szPublisher); pXml->AddElement(_T("Preparer"),g_ProjectSettings.m_szPreparer); pXml->AddElement(_T("System"),g_ProjectSettings.m_szSystem); pXml->AddElement(_T("VolumeSet"),g_ProjectSettings.m_szVolumeSet); pXml->AddElement(_T("Files"),_T(""),true); pXml->AddElement(_T("Copyright"),g_ProjectSettings.m_szCopyright); pXml->AddElement(_T("Abstract"),g_ProjectSettings.m_szAbstract); pXml->AddElement(_T("Bibliographic"),g_ProjectSettings.m_szBibliographic); pXml->LeaveElement(); pXml->LeaveElement(); } bool CProjectManager::LoadProjectFields(CXmlProcessor *pXml) { if (!pXml->EnterElement(_T("Fields"))) return false; pXml->GetSafeElementData(_T("Publisher"),g_ProjectSettings.m_szPublisher,127); pXml->GetSafeElementData(_T("Preparer"),g_ProjectSettings.m_szPreparer,127); pXml->GetSafeElementData(_T("System"),g_ProjectSettings.m_szSystem,127); pXml->GetSafeElementData(_T("VolumeSet"),g_ProjectSettings.m_szVolumeSet,127); if (!pXml->EnterElement(_T("Files"))) { pXml->LeaveElement(); return false; } pXml->GetSafeElementData(_T("Copyright"),g_ProjectSettings.m_szCopyright,36); pXml->GetSafeElementData(_T("Abstract"),g_ProjectSettings.m_szAbstract,36); pXml->GetSafeElementData(_T("Bibliographic"),g_ProjectSettings.m_szBibliographic,36); pXml->LeaveElement(); pXml->LeaveElement(); return true; } void CProjectManager::SaveProjectBoot(CXmlProcessor *pXml) { pXml->AddElement(_T("Boot"),_T(""),true); pXml->AddElement(_T("Images"),_T(""),true); int iCounter = 0; TCHAR szName[32]; std::list ::iterator itNodeObject; for (itNodeObject = g_ProjectSettings.m_BootImages.begin(); itNodeObject != g_ProjectSettings.m_BootImages.end(); itNodeObject++) { CProjectBootImage *pBootImage = *itNodeObject; lsnprintf_s(szName,32,_T("Image%d"),iCounter); pXml->AddElement(szName,_T(""),true); pXml->AddElement(_T("FullPath"),pBootImage->m_FullPath.c_str()); pXml->AddElement(_T("LocalName"),pBootImage->m_LocalName.c_str()); pXml->AddElement(_T("Emulation"),pBootImage->m_iEmulation); pXml->AddElement(_T("NoBoot"),pBootImage->m_bNoBoot); pXml->AddElement(_T("LoadSegment"),pBootImage->m_uiLoadSegment); pXml->AddElement(_T("LoadSize"),pBootImage->m_uiLoadSize); pXml->LeaveElement(); } pXml->LeaveElement(); pXml->LeaveElement(); } bool CProjectManager::LoadProjectBoot(CXmlProcessor *pXml) { if (!pXml->EnterElement(_T("Boot"))) return false; if (!pXml->EnterElement(_T("Images"))) { pXml->LeaveElement(); return false; } TCHAR szFileName[MAX_PATH]; for (unsigned int i = 0; i < pXml->GetElementChildCount(); i++) { if (!pXml->EnterElement(i)) { pXml->LeaveElement(); pXml->LeaveElement(); return false; } CProjectBootImage *pBootImage = new CProjectBootImage(); pXml->GetSafeElementData(_T("FullPath"),szFileName,MAX_PATH - 1); pBootImage->m_FullPath = szFileName; pXml->GetSafeElementData(_T("LocalName"),szFileName,MAX_PATH - 1); pBootImage->m_LocalName = szFileName; pXml->GetSafeElementData(_T("Emulation"),&pBootImage->m_iEmulation); pXml->GetSafeElementData(_T("NoBoot"),&pBootImage->m_bNoBoot); int iLoadSegment = 0; pXml->GetSafeElementData(_T("LoadSegment"),&iLoadSegment); pBootImage->m_uiLoadSegment = static_cast(iLoadSegment); int iLoadSize = 0; pXml->GetSafeElementData(_T("LoadSize"),&iLoadSize); pBootImage->m_uiLoadSize = static_cast(iLoadSize); g_ProjectSettings.m_BootImages.push_back(pBootImage); pXml->LeaveElement(); } pXml->LeaveElement(); pXml->LeaveElement(); return true; } /** Saves the current project to the specified file. The file will be created if it does not exists and overwritten otherwise. @param szFullPath the absolute path to a project file on the file system. @return true if the project was successfully saved, false otherwise. */ bool CProjectManager::SaveProject(const TCHAR *szFullPath) { CXmlProcessor Xml; Xml.AddElement(_T("InfraRecorder"),_T(""),true); Xml.AddElement(_T("Project"),_T(""),true); Xml.AddElementAttr(_T("version"),PROJECTMANAGER_FILEVERSION); Xml.AddElementAttr(_T("type"),m_iProjectType); Xml.AddElementAttr(_T("media"),m_iProjectMedia); switch (m_iProjectType) { case PROJECTTYPE_DATA: Xml.AddElement(_T("Label"),g_ProjectSettings.m_szLabel); SaveProjectFileSys(&Xml); SaveProjectISO(&Xml); SaveProjectFields(&Xml); SaveProjectBoot(&Xml); break; case PROJECTTYPE_AUDIO: Xml.AddElement(_T("AlbumName"),g_ProjectSettings.m_szAlbumName); Xml.AddElement(_T("AlbumArtist"),g_ProjectSettings.m_szAlbumArtist); break; case PROJECTTYPE_MIXED: Xml.AddElement(_T("Label"),g_ProjectSettings.m_szLabel); Xml.AddElement(_T("AlbumName"),g_ProjectSettings.m_szAlbumName); Xml.AddElement(_T("AlbumArtist"),g_ProjectSettings.m_szAlbumArtist); SaveProjectFileSys(&Xml); SaveProjectISO(&Xml); SaveProjectFields(&Xml); break; }; SaveProjectData(&Xml); Xml.LeaveElement(); Xml.LeaveElement(); return Xml.Save(szFullPath) == XMLRES_OK; } /** Loads project data from the specified file. @param szFullPath the absolute path to a project file on the file system. @return true if the project was successfully loaded, false otherwise. */ bool CProjectManager::LoadProject(const TCHAR *szFullPath) { CXmlProcessor Xml; int iResult = Xml.Load(szFullPath); if (iResult != XMLRES_OK && iResult != XMLRES_FILEERROR) { TCHAR szMessage[128]; lsnprintf_s(szMessage,128,lngGetString(ERROR_LOADPROJECTXML),iResult); MessageBox(*g_pMainFrame,szMessage,lngGetString(GENERAL_ERROR),MB_OK | MB_ICONERROR); return false; } if (!Xml.EnterElement(_T("InfraRecorder"))) return false; if (!Xml.EnterElement(_T("Project"))) return false; // Version check. int iVersion = 0; Xml.GetSafeElementAttrValue(_T("version"),&iVersion); if (iVersion > PROJECTMANAGER_FILEVERSION) { lngMessageBox(*g_pMainFrame,ERROR_PROJECTVERSION,GENERAL_ERROR,MB_OK | MB_ICONERROR); return false; } if (iVersion < PROJECTMANAGER_FILEVERSION) lngMessageBox(*g_pMainFrame,WARNING_OLDPROJECT,GENERAL_WARNING,MB_OK | MB_ICONWARNING); // Project type. int iType = -1; Xml.GetSafeElementAttrValue(_T("type"),&iType); int iMedia = false; Xml.GetSafeElementAttrValue(_T("media"),&iMedia); switch (iType) { case PROJECTTYPE_DATA: NewDataProject(iMedia); // Label. Xml.GetSafeElementData(_T("Label"),g_ProjectSettings.m_szLabel,MAX_PATH - 1); SetDiscLabel(g_ProjectSettings.m_szLabel); // Data information. LoadProjectFileSys(&Xml); LoadProjectISO(&Xml); LoadProjectFields(&Xml); LoadProjectBoot(&Xml); break; case PROJECTTYPE_AUDIO: NewAudioProject(iMedia); // Album information. Xml.GetSafeElementData(_T("AlbumName"),g_ProjectSettings.m_szAlbumName,159); Xml.GetSafeElementData(_T("AlbumArtist"),g_ProjectSettings.m_szAlbumArtist,159); break; case PROJECTTYPE_MIXED: NewMixedProject(iMedia); // Label. Xml.GetSafeElementData(_T("Label"),g_ProjectSettings.m_szLabel,MAX_PATH - 1); SetDiscLabel(g_ProjectSettings.m_szLabel); // Album information. Xml.GetSafeElementData(_T("AlbumName"),g_ProjectSettings.m_szAlbumName,159); Xml.GetSafeElementData(_T("AlbumArtist"),g_ProjectSettings.m_szAlbumArtist,159); // Data information. LoadProjectFileSys(&Xml); LoadProjectISO(&Xml); LoadProjectFields(&Xml); break; default: lngMessageBox(*g_pMainFrame,ERROR_LOADPROJECT,GENERAL_ERROR,MB_OK | MB_ICONERROR); return false; } // Project data. if (!LoadProjectData(&Xml)) { lngMessageBox(*g_pMainFrame,ERROR_LOADPROJECT,GENERAL_ERROR,MB_OK | MB_ICONERROR); return false; } // Try to expand the root item for data projects. if (iType == PROJECTTYPE_DATA) m_pTreeView->Expand(g_TreeManager.GetRootNode()->m_hTreeItem); // Update the space meter. if (m_pSpaceMeter != NULL) m_pSpaceMeter->SetAllocatedSize(g_TreeManager.GetNodeSize(g_TreeManager.GetRootNode())); Xml.LeaveElement(); Xml.LeaveElement(); return true; } /** Obtains project information. @param uiFileCount number of files in the project. @param uiFolderCount number of folders in the project. @param uiTrackCount number of tracks in the project. */ void CProjectManager::GetProjectContents(unsigned __int64 &uiFileCount,unsigned __int64 &uiFolderCount, unsigned __int64 &uiTrackCount) { switch (m_iProjectType) { case PROJECTTYPE_DATA: g_TreeManager.GetNodeContents(g_TreeManager.GetRootNode(),uiFileCount,uiFolderCount); uiTrackCount = 0; break; case PROJECTTYPE_AUDIO: g_TreeManager.GetNodeContents(g_TreeManager.GetRootNode(),uiTrackCount,uiFolderCount); uiFileCount = 0; uiFolderCount = 0; break; case PROJECTTYPE_MIXED: g_TreeManager.GetNodeContents(m_pMixAudioNode,uiTrackCount,uiFolderCount); g_TreeManager.GetNodeContents(m_pMixDataNode,uiFileCount,uiFolderCount); break; }; } /** Returns the project size in bytes. @return the project size in bytes. */ unsigned __int64 CProjectManager::GetProjectSize() { return m_pSpaceMeter->GetAllocatedSize(); } /* CProjectManager::GetProjectAudioSize ------------------------------------ Returns the number of bytes of CD audio that the project contains. */ // Working, but not used. /*unsigned __int64 CProjectManager::GetProjectAudioSize() { switch (GetProjectType()) { case PROJECTTYPE_AUDIO: return GetProjectSize(); case PROJECTTYPE_MIXED: return g_TreeManager.GetNodeSize(m_pMixAudioNode); } return 0; }*/ /** Returns the data root node of a mixed mode project. @return the data root node of a mixed mode project. */ CProjectNode *CProjectManager::GetMixDataRootNode() { return m_pMixDataNode; } /** Returns the audio root node of a mixed mode project. @return the audio root node of a mixed mode project. */ CProjectNode *CProjectManager::GetMixAudioRootNode() { return m_pMixAudioNode; } /** Updates the specifed list view with all audio files in an audio or mixed mode project. @param pListView the list view which should be updated. */ void CProjectManager::ListAudioTracks(CListViewCtrl *pListView) { if (m_iProjectType == PROJECTTYPE_AUDIO) g_TreeManager.ListNodeFiles(g_TreeManager.GetRootNode(),pListView); else if (m_iProjectType == PROJECTTYPE_MIXED) g_TreeManager.ListNodeFiles(m_pMixAudioNode,pListView); } /** Fills the specified vector with the absolute file system paths of all audio tracks in project. @param AudioTracks the target vector which should be updated with the absolute paths. */ void CProjectManager::GetAudioTracks(std::vector &AudioTracks) { if (m_iProjectType == PROJECTTYPE_AUDIO) g_TreeManager.GetNodeFullPaths(g_TreeManager.GetRootNode(),AudioTracks); else if (m_iProjectType == PROJECTTYPE_MIXED) g_TreeManager.GetNodeFullPaths(m_pMixAudioNode,AudioTracks); } /** Decodes the specified audio file to a file with the specified temporary file path. @param szFullPath absolute path to the file to be decoded. @param szFullTempPath absolute path to the decoded file which should be created. @param pProgress progress feedback object. @return true if successfull, false otherwise. */ bool CProjectManager::DecodeAudioTrack(const TCHAR *szFullPath,const TCHAR *szFullTempPath, CAdvancedProgress *pProgress) { // Find which codec that can be uses for decoding the source file. CCodec *pDecoder = NULL; // Audio file information. int iNumChannels = -1; int iSampleRate = -1; int iBitRate = -1; unsigned __int64 uiDuration = 0; for (unsigned int i = 0; i < g_CodecManager.m_Codecs.size(); i++) { // We're only interested in decoders. if ((g_CodecManager.m_Codecs[i]->irc_capabilities() & IRC_HAS_DECODER) == 0) continue; if (g_CodecManager.m_Codecs[i]->irc_decode_init(szFullPath,iNumChannels, iSampleRate,iBitRate,uiDuration)) { pDecoder = g_CodecManager.m_Codecs[i]; break; } } if (pDecoder == NULL) { TCHAR szNameBuffer[MAX_PATH]; lstrcpy(szNameBuffer,szFullPath); ExtractFileName(szNameBuffer); pProgress->notify(ckcore::Progress::ckERROR,lngGetString(ERROR_NODECODER),szNameBuffer); return false; } // Find the wave encoder. CCodec *pEncoder = NULL; for (unsigned int i = 0; i < g_CodecManager.m_Codecs.size(); i++) { if ((g_CodecManager.m_Codecs[i]->irc_capabilities() & IRC_HAS_ENCODER) == 0) continue; if (!lstrcmp(g_CodecManager.m_Codecs[i]->irc_string(IRC_STR_FILEEXT),_T(".wav"))) { pEncoder = g_CodecManager.m_Codecs[i]; break; } } if (pEncoder == NULL) { pProgress->notify(ckcore::Progress::ckERROR,lngGetString(ERROR_WAVECODEC)); pDecoder->irc_decode_exit(); return false; } // Initialize the encoder. if (!pEncoder->irc_encode_init(szFullTempPath,iNumChannels,iSampleRate,iBitRate)) { pProgress->notify(ckcore::Progress::ckERROR,lngGetString(ERROR_CODECINIT), pEncoder->irc_string(IRC_STR_ENCODER), iNumChannels,iSampleRate,iBitRate,uiDuration); pDecoder->irc_decode_exit(); return false; } // Encode/decode-process. __int64 iBytesRead = 0; unsigned __int64 uiCurrentTime = 0; // FIXME: This macro should not be placed here. #define ENCODE_BUFFER_FACTOR 1024 // Allocate buffer memory. unsigned int uiBufferSize = iNumChannels * ((iBitRate / iSampleRate) >> 3) * ENCODE_BUFFER_FACTOR; unsigned char *pBuffer = new unsigned char[uiBufferSize]; while (true) { iBytesRead = pDecoder->irc_decode_process(pBuffer,uiBufferSize,uiCurrentTime); if (iBytesRead <= 0) break; if (pEncoder->irc_encode_process(pBuffer,iBytesRead) < 0) { pProgress->notify(ckcore::Progress::ckERROR,lngGetString(ERROR_ENCODEDATA)); break; } // Update the progres bar. unsigned char ucPercent = (unsigned char)(((double)uiCurrentTime/uiDuration) * 100); pProgress->set_progress(ucPercent); } // Free buffer memory. delete [] pBuffer; // Flush. pEncoder->irc_encode_flush(); pProgress->set_progress(100); // Destroy the codecs. pEncoder->irc_encode_exit(); pDecoder->irc_decode_exit(); TCHAR szNameBuffer[MAX_PATH]; lstrcpy(szNameBuffer,szFullPath); ExtractFileName(szNameBuffer); pProgress->notify(ckcore::Progress::ckINFORMATION, lngGetString(SUCCESS_DECODETRACK),szNameBuffer); return true; } /** Decodes any necessary (that are not in a compatible format) track in the specified audio tracks vector. The decoded audio tracks vector will be updated with the new temporary file paths of the decoded tracks. Please note that the caller needs to free the memory allocated for the strings added to the decoded tracks vector. @param AudioTracks vector of aboslute file paths to audio tracks that should be decoded. @param DecodedTracks output vector of absolute file paths to the decoded tracks. @param pProgress progress feedback object. @return true if successfull, false otherwise. */ bool CProjectManager::DecodeAudioTracks(std::vector &AudioTracks, std::vector &DecodedTracks, CAdvancedProgress *pProgress) { if (pProgress == NULL) return false; for (unsigned int i = 0; i < AudioTracks.size(); i++) { // Return if the user has canceled the operaiton. if (pProgress->cancelled()) return false; // If the track isn't a wave file it needs to be decoded. if (GetAudioFormat(AudioTracks[i]) != AUDIOFORMAT_WAVE) { TCHAR szFileName[MAX_PATH]; lstrcpy(szFileName,AudioTracks[i]); ExtractFileName(szFileName); // Create temporary file name. TCHAR *szTempName = new TCHAR[MAX_PATH]; lstrcpy(szTempName,g_GlobalSettings.m_szTempPath); lstrcat(szTempName,szFileName); ChangeFileExt(szTempName,_T(".wav")); // Decode the track. if (DecodeAudioTrack(AudioTracks[i],szTempName,pProgress)) { DecodedTracks.push_back(szTempName); AudioTracks[i] = szTempName; } else { delete [] szTempName; return false; } } } return true; } /** Saves the project CD-Text data to the specified file. @param szFullPath the absolute path of the file that should contain the CD-Text data. The file will be created if it doesn't exist. If it already exists it will be overwritten. @return true if the file was successfully created, false otherwise. */ bool CProjectManager::SaveCDText(const TCHAR *szFullPath) { std::vector Files; switch (m_iProjectType) { case PROJECTTYPE_MIXED: g_TreeManager.GetNodeFiles(m_pMixAudioNode,Files); break; case PROJECTTYPE_AUDIO: g_TreeManager.GetNodeFiles(g_TreeManager.GetRootNode(),Files); break; }; CCdText CdText; return CdText.WriteFileEx(szFullPath,g_ProjectSettings.m_szAlbumName,g_ProjectSettings.m_szAlbumArtist,Files); } /** Verifies all files in the specified folder (node). The number of failed readings will be obtained. @param pNode folder (node) containing all files to be verified. @param FolderStack vector of folders (nodes) that will be updated as new sub folders are detected. @param pProgress progress feedback object. @param szFileNameBuffer file name buffer used for improving performance. @param iPathStripLen number of characters that should be stripped from the current project path. @param pCrc32File helper object for calculating a CRC32 checksum. @param uiFailCount number of files that failed the CRC32 verification. @return true if completed (with or without errors), and false if cancelled. */ bool CProjectManager::VerifyLocalFiles(CProjectNode *pNode,std::vector &FolderStack, CAdvancedProgress *pProgress,TCHAR *szFileNameBuffer,int iPathStripLen, ckcore::Progresser &FileProgresser,unsigned __int64 &uiFailCount, std::map &FilePathMap) { ckcore::CrcStream FileCrcStream(ckcore::CrcStream::ckCRC_32); TCHAR szStatus[MAX_PATH + 32]; tstring FileName; TCHAR szDriveLetter[3]; szDriveLetter[0] = szFileNameBuffer[0]; szDriveLetter[1] = szFileNameBuffer[1]; szDriveLetter[2] = '\0'; std::list ::iterator itNodeObject; for (itNodeObject = pNode->m_Children.begin(); itNodeObject != pNode->m_Children.end(); itNodeObject++) FolderStack.push_back(*itNodeObject); std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) { CItemData *pItemData = (*itFileObject); // Ignore files that are already on the disc. We have nothing to // compare them against. if (pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) continue; // Don't overwrite the drive letter. lstrcpy(szFileNameBuffer + 2,pItemData->GetFilePath() + iPathStripLen); lstrcat(szFileNameBuffer,pItemData->GetFileName()); lsnprintf_s(szStatus,MAX_PATH + 32,lngGetString(STATUS_VERIFY),szFileNameBuffer); pProgress->set_status(szStatus); // Calculate CRC of file on the hard drive. ckcore::FileInStream FileStream1(pItemData->szFullPath); if (!FileStream1.open()) return false; FileCrcStream.reset(); if (!ckcore::stream::copy(FileStream1,FileCrcStream,FileProgresser)) return false; FileStream1.close(); unsigned long ulGoodCrc = FileCrcStream.checksum(); // Calculate CRC of the file on the disc. FileName = szDriveLetter; FileName.append(FilePathMap[szFileNameBuffer + 2]); ckcore::FileInStream FileStream2(FileName.c_str()); if (!FileStream2.open()) return false; FileCrcStream.reset(); if (!ckcore::stream::copy(FileStream2,FileCrcStream,FileProgresser)) return false; FileStream2.close(); unsigned long ulTestCrc = FileCrcStream.checksum(); // Compare the CRC of the file on the disc to the one on the harddrive. if (ulTestCrc != ulGoodCrc) { if (ulTestCrc == 0) { pProgress->notify(ckcore::Progress::ckERROR, lngGetString(FAILURE_VERIFYNOFILE),FileName.c_str() + 3); } else { pProgress->notify(ckcore::Progress::ckERROR, lngGetString(FAILURE_VERIFYREADERROR),/*szFileNameBuffer*/FileName.c_str(),ulTestCrc,ulGoodCrc); } uiFailCount++; } } return true; } /** Performs a CRC check comparission on the files on the hard disk and the CD. @param pProgress progress feedback object. @param szDriveLetter drive letter of the device containg the CD to be verified. @return true of the operation completed successfully (with or without errors), and false if the operation was cancelled. */ bool CProjectManager::VerifyCompilation(CAdvancedProgress *pProgress,const TCHAR *szDriveLetter, std::map &FilePathMap) { int iPathStripLen = 0; CProjectNode *pRootNode = NULL; switch (g_ProjectManager.GetProjectType()) { case PROJECTTYPE_MIXED: pRootNode = GetMixDataRootNode(); iPathStripLen = lstrlen(pRootNode->pItemData->GetFileName()) + 1; break; default: pRootNode = g_TreeManager.GetRootNode(); break; } pProgress->notify(ckcore::Progress::ckINFORMATION,lngGetString(PROGRESS_BEGINVERIFY)); // It's important the the first two characters contain :. TCHAR szFileNameBuffer[MAX_PATH]; lstrcpy(szFileNameBuffer,szDriveLetter); unsigned __int64 uiFailCount = 0; ckcore::Progresser FileProgresser(*pProgress,g_TreeManager.GetNodeSize(pRootNode) << 1); std::vector FolderStack; if (!VerifyLocalFiles(pRootNode,FolderStack,pProgress,szFileNameBuffer,iPathStripLen,FileProgresser,uiFailCount,FilePathMap)) return false; while (FolderStack.size() > 0) { pRootNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); if (!VerifyLocalFiles(pRootNode,FolderStack,pProgress,szFileNameBuffer,iPathStripLen,FileProgresser,uiFailCount,FilePathMap)) return false; } // Display the final message. if (uiFailCount == 0) { pProgress->notify(ckcore::Progress::ckINFORMATION, lngGetString(SUCCESS_VERIFY)); } else { pProgress->notify(ckcore::Progress::ckINFORMATION, lngGetString(FAILURE_VERIFY),uiFailCount); } return true; } /** Updates the label of the current project. @param szLabelName new label. */ void CProjectManager::SetDiscLabel(TCHAR *szLabelName) { switch (m_iProjectType) { case PROJECTTYPE_DATA: if (m_pTreeView != NULL) m_pTreeView->SetItemText(g_TreeManager.GetRootNode()->m_hTreeItem,szLabelName); break; case PROJECTTYPE_AUDIO: szLabelName[0] = '\0'; break; case PROJECTTYPE_MIXED: if (m_pTreeView != NULL) m_pTreeView->SetItemText(m_pMixDataNode->m_hTreeItem,szLabelName); break; }; } /** Updates the modified status of the current project. @param bModified true if the project has been modified after last save, false otherwise. */ void CProjectManager::SetModified(bool bModified) { m_bModified = bModified; } /** Returns the modified status of the current project. @return the modified status of the current project. */ bool CProjectManager::GetModified() { return m_bModified; } bool CProjectManager::IsEmpty() const { switch (m_iProjectType) { case PROJECTTYPE_DATA: case PROJECTTYPE_AUDIO: return g_TreeManager.GetRootNode()->m_Children.size() == 0; case PROJECTTYPE_MIXED: return m_pMixAudioNode->m_Children.size() == 0 && m_pMixDataNode->m_Children.size() == 0; default: assert(false); break; }; return false; } /** * Imports a single file into the project. * @param [in] BasePath The base path to use in order to build full path if the * specified file path is relative. * @param [in] FilePath The full or relative file path. * @param [in] Transaction The transaction object to update with the new file. * @return If successful true is returned, if not false is returned. */ bool CProjectManager::ImportFile(ckcore::Path &BasePath, ckcore::tstring &FilePath, CFileTransaction &Transaction) { // Check if full file path. bool bFullPath = FilePath.size() > 1 && (FilePath[1] == ':' || (FilePath[0] == '\\' && FilePath[1] == '\\')); if (bFullPath) return Transaction.AddFile(FilePath.c_str()); // Create full path from relative path. ckcore::Path FullPath = BasePath; FullPath += FilePath.c_str(); return Transaction.AddFile(FullPath.name().c_str()); } /** * Imports data from a file list (text file containing one file or folder on * each line). The file can be in M3U format, supporting comments starting with * the '#'-character. * @param [in] szFullPath Path to the file list. * @return If successful true is returned, if not false is returned. */ bool CProjectManager::Import(const TCHAR *szFullPath) { // Open the selected file for reading. ckcore::FileInStream FileStream(szFullPath); if (!FileStream.open()) return false; // Calculate the base path name in case the listed files have relative paths. ckcore::Path BasePath(szFullPath); BasePath = BasePath.dir_name().c_str(); CFileTransaction Transaction; // Read the file line by line. ckcore::LineReader::Encoding FileEnc = ckcore::LineReader::encoding(FileStream); FileStream.seek(0,ckcore::InStream::ckSTREAM_BEGIN); // Check if ANSI or UTF-16 encoding. if (FileEnc == ckcore::LineReader::ckENCODING_ANSI) { ckcore::LineReader LineReader(FileStream); while (!LineReader.end()) { ckcore::tstring Line = ckcore::string::ansi_to_auto<1024>(LineReader.read_line().c_str()); // Skip empty and commented lines. if (Line.empty()) continue; if (Line[0] == '#') continue; // Remove any trailing path delimiters. if (Line[Line.size() - 1] == '\\' || Line[Line.size() - 1] == '/') Line.resize(Line.size() - 1); if (!ImportFile(BasePath,Line,Transaction)) { TCHAR szBuffer[1024]; lsprintf(szBuffer,lngGetString(ERROR_PROJECT_IMPORT_FILE), Line.c_str()); MessageBox(HWND_DESKTOP,szBuffer,lngGetString(GENERAL_ERROR), MB_OK | MB_ICONERROR); } } } else { ckcore::LineReader LineReader(FileStream); while (!LineReader.end()) { ckcore::tstring Line = ckcore::string::utf16_to_auto<1024>(LineReader.read_line().c_str()); // Skip empty and commented lines. if (Line.empty()) continue; if (Line[0] == '#') continue; // Remove any trailing path delimiters. if (Line[Line.size() - 1] == '\\' || Line[Line.size() - 1] == '/') Line.resize(Line.size() - 1); if (!ImportFile(BasePath,Line,Transaction)) { TCHAR szBuffer[1024]; lsprintf(szBuffer,lngGetString(ERROR_PROJECT_IMPORT_FILE), Line.c_str()); MessageBox(HWND_DESKTOP,szBuffer,lngGetString(GENERAL_ERROR), MB_OK | MB_ICONERROR); } } } return true; } ================================================ FILE: src/app/project_manager.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include #include #include "space_meter.hh" #include "tree_manager.hh" #include "custom_container.hh" #include "advanced_progress.hh" #include "confirm_file_replace_dlg.hh" // Specifies what column index each data column has. #define COLUMN_SUBINDEX_NAME 0 #define COLUMN_SUBINDEX_SIZE 1 #define COLUMN_SUBINDEX_TYPE 2 #define COLUMN_SUBINDEX_MODIFIED 3 #define COLUMN_SUBINDEX_PATH 4 // Specifies what column index each audio column has. #define COLUMN_SUBINDEX_TRACK 0 #define COLUMN_SUBINDEX_TITLE 1 #define COLUMN_SUBINDEX_LENGTH 2 #define COLUMN_SUBINDEX_LOCATION 3 #define PROJECTVIEWTYPE_DATA 0 #define PROJECTVIEWTYPE_AUDIO 1 #define PROJECTTYPE_DATA 0 #define PROJECTTYPE_AUDIO 1 #define PROJECTTYPE_MIXED 2 // What project file version does this build use. #define PROJECTMANAGER_FILEVERSION 3 /// Class for project content management. /** Implements core project functionallity such as creating and loading projects, adding, removing and moving files. */ class CProjectManager { public: /// Class for performing file transactions within a project. /** Implements support for adding and moving files to/within a project. */ class CFileTransaction { public: enum eMode { MODE_NORMAL, MODE_IMPORT }; private: eMode m_Mode; CConfirmFileReplaceDlg m_ReplaceDlg; void AddFilesInFolder(CProjectNode *pParentNode,std::vector &FolderStack); bool AddDataFile(CProjectNode *pParentNode,const TCHAR *szFileName, const TCHAR *szFilePath,const TCHAR *szFullPath,FILETIME *pFileTime, unsigned __int64 uiSize); CItemData *AddDataFile(CProjectNode *pParentNode,const TCHAR *szFullPath); CProjectNode *AddFolder(CProjectNode *pParentNode,const TCHAR *szFolderName, const TCHAR *szFolderPath,const TCHAR *szFullPath,FILETIME *pFileTime); CProjectNode *AddFolder(CProjectNode *pParentNode,const TCHAR *szFullPath); bool AddAudioFile(CProjectNode *pParentNode,const TCHAR *szFullPath); public: CFileTransaction(eMode Mode = MODE_NORMAL); ~CFileTransaction(); bool AddFile(const TCHAR *szFullPath,CProjectNode *pTargetNode = NULL); CItemData *AddFile(const TCHAR *szFullPath,const TCHAR *szProjectPath); bool MoveFile(CProjectNode *pItemParent,CItemData *pItemData,CProjectNode *pNewParent); bool MoveFileToCurrent(CProjectNode *pItemParent,CItemData *pItemData); }; private: int m_iProjectType; int m_iProjectMedia; int m_iViewType; int m_iActiveView; // Tells us what view (tree or list) that last had focus. bool m_bModified; // Set to true if the project has been modified since the last save. CProjectNode *m_pActionNode; // Used for random internal temporary purposes. CSplitterWindow *m_pProjectView; CCustomContainer *m_pContainer; CSpaceMeter *m_pSpaceMeter; CListViewCtrl *m_pListView; CTreeViewCtrlEx *m_pTreeView; CProjectNode *m_pMixDataNode; CProjectNode *m_pMixAudioNode; void SetupDataListView(); void SetupAudioListView(); bool DecodeAudioTrack(const TCHAR *szFullPath,const TCHAR *szFullTempPath, CAdvancedProgress *pProgress); bool VerifyLocalFiles(CProjectNode *pNode,std::vector &FolderStack, CAdvancedProgress *pProgress,TCHAR *szFileNameBuffer,int iPathStripLen, ckcore::Progresser &FileProgresser,unsigned __int64 &uiFailCount, std::map &FilePathMap); bool GenerateNewFolderName(CProjectNode *pParent,TCHAR *szFolderName, unsigned int uiFolderNameSize); void CloseProject(); void SaveProjectData(CXmlProcessor *pXML); bool LoadProjectData(CXmlProcessor *pXML); void SaveProjectFileSys(CXmlProcessor *pXML); bool LoadProjectFileSys(CXmlProcessor *pXML); void SaveProjectISO(CXmlProcessor *pXML); bool LoadProjectISO(CXmlProcessor *pXML); void SaveProjectFields(CXmlProcessor *pXML); bool LoadProjectFields(CXmlProcessor *pXML); void SaveProjectBoot(CXmlProcessor *pXML); bool LoadProjectBoot(CXmlProcessor *pXML); enum eActiveView { AV_TREE, AV_LIST }; bool ImportFile(ckcore::Path &BasePath,ckcore::tstring &FilePath, CFileTransaction &Transaction); public: CProjectManager(); ~CProjectManager(); LRESULT OnNewFolder(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnRename(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnRemove(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); void AssignControls(CSplitterWindow *pProjectView,CCustomContainer *pContainer, CSpaceMeter *pSpaceMeter,CListViewCtrl *pListView,CTreeViewCtrlEx *pTreeView); void EnableAll(int iID,bool bEnable,HMENU hMenu = NULL); void NewDataProject(int iDiscMedia); void NewAudioProject(int iDiscMedia); void NewMixedProject(int iDiscMedia); void DataSelected(); void AudioSelected(); bool ListAddNewFolder(); bool TreeAddNewFolder(CProjectNode *pParentNode); void RemoveFile(CProjectNode *pParentNode,CItemData *pItemData); void ListRemoveSel(); void TreeRemoveNode(CProjectNode *pNode); void NotifyListSelChanged(unsigned int uiSelCount); void NotifyTreeSelChanged(CProjectNode *pNode); void TreeSetActionNode(CProjectNode *pNode); void TreeSetActive(); void ListSetActive(); void DeleteImportedItems(); int GetViewType(); int GetProjectType(); void GetProjectContents(unsigned __int64 &uiFileCount,unsigned __int64 &uiFolderCount, unsigned __int64 &uiTrackCount); unsigned __int64 GetProjectSize(); //unsigned __int64 GetProjectAudioSize(); CProjectNode *GetMixDataRootNode(); CProjectNode *GetMixAudioRootNode(); void ListAudioTracks(CListViewCtrl *pListView); void GetAudioTracks(std::vector &AudioTracks); bool DecodeAudioTracks(std::vector &AudioTracks, std::vector &DecodedTracks,CAdvancedProgress *pProgress); bool SaveCDText(const TCHAR *szFullPath); bool VerifyCompilation(CAdvancedProgress *pProgress,const TCHAR *szDriveLetter, std::map &FilePathMap); void SetDiscLabel(TCHAR *szLabelName); void SetModified(bool bModified); bool GetModified(); bool IsEmpty() const; bool SaveProject(const TCHAR *szFullPath); bool LoadProject(const TCHAR *szFullPath); bool Import(const TCHAR *szFullPath); }; extern CProjectManager g_ProjectManager; ================================================ FILE: src/app/registry.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "registry.hh" CRegistry::CRegistry() { m_hRootKey = HKEY_CURRENT_USER; } CRegistry::~CRegistry() { } void CRegistry::SetRoot(HKEY hKey) { m_hRootKey = hKey; } bool CRegistry::OpenKey(const TCHAR *szKeyName,bool bCreate) { if (RegOpenKeyEx(m_hRootKey,szKeyName,0,KEY_ALL_ACCESS,&m_hKey) == ERROR_SUCCESS) return true; if (bCreate) { DWORD dwResult; if (RegCreateKeyEx(m_hRootKey,szKeyName,0,NULL,REG_OPTION_NON_VOLATILE,KEY_ALL_ACCESS,NULL,&m_hKey,&dwResult) == ERROR_SUCCESS) return true; } return false; } bool CRegistry::CloseKey() { if (RegCloseKey(m_hKey) == ERROR_SUCCESS) return true; return false; } bool CRegistry::DeleteKey(const TCHAR *szKeyName) { if (RegDeleteKey(m_hKey,szKeyName) == ERROR_SUCCESS) return true; return false; } bool CRegistry::ReadBool(const TCHAR *szValueName,bool &bResult) { DWORD dwValue,dwSize = sizeof(DWORD),dwType = REG_DWORD; if (RegQueryValueEx(m_hKey,szValueName,NULL,&dwType,(LPBYTE)&dwValue,&dwSize) == ERROR_SUCCESS) { bResult = dwValue >= 1 ? true : false; return true; } return false; } bool CRegistry::ReadInteger(const TCHAR *szValueName,int &iResult) { DWORD dwValue,dwSize = sizeof(DWORD),dwType = REG_DWORD; if (RegQueryValueEx(m_hKey,szValueName,NULL,&dwType,(LPBYTE)&dwValue,&dwSize) == ERROR_SUCCESS) { iResult = (int)dwValue; return true; } return false; } bool CRegistry::ReadInteger64(const TCHAR *szValueName,__int64 &iResult) { DWORD dwSize = sizeof(__int64),dwType = REG_QWORD; LARGE_INTEGER liValue; if (RegQueryValueEx(m_hKey,szValueName,NULL,&dwType,(LPBYTE)&liValue,&dwSize) == ERROR_SUCCESS) { iResult = (__int64)liValue.QuadPart; return true; } return false; } bool CRegistry::ReadString(const TCHAR *szValueName,TCHAR *szResult, unsigned long ulBufferSize) { DWORD dwBufferSize = ulBufferSize; if (RegQueryValueEx(m_hKey,szValueName,NULL,NULL,(LPBYTE)szResult, &dwBufferSize) == ERROR_SUCCESS) { return true; } return false; } bool CRegistry::ReadStringEx(const TCHAR *szValueName,TCHAR *&szResult) { unsigned long ulBufferSize = STRING_CHUNK_SIZE; szResult = new TCHAR[STRING_CHUNK_SIZE]; long lResult = 0; while ((lResult = RegQueryValueEx(m_hKey,szValueName,NULL,NULL,(LPBYTE)szResult, &ulBufferSize)) == ERROR_MORE_DATA) { // Increase the buffer size. ulBufferSize += STRING_CHUNK_SIZE; // Reallocate memory for the buffer. Why doesn't the realloc code work? //realloc(szResult,ulBufferSize); delete [] szResult; szResult = new TCHAR[ulBufferSize]; } if (lResult != ERROR_SUCCESS) { delete [] szResult; return false; } return true; } bool CRegistry::WriteBool(const TCHAR *szValueName,bool bValue) { DWORD dwValue = (DWORD)bValue; if (RegSetValueEx(m_hKey,szValueName,NULL,(DWORD)REG_DWORD,(LPBYTE)&dwValue, (DWORD)sizeof(DWORD)) == ERROR_SUCCESS) { return true; } return false; } bool CRegistry::WriteInteger(const TCHAR *szValueName,int iValue) { DWORD dwValue = (DWORD)iValue; if (RegSetValueEx(m_hKey,szValueName,NULL,(DWORD)REG_DWORD,(LPBYTE)&dwValue, (DWORD)sizeof(DWORD)) == ERROR_SUCCESS) { return true; } return false; } bool CRegistry::WriteInteger64(const TCHAR *szValueName,__int64 iValue) { LARGE_INTEGER liValue; liValue.QuadPart = iValue; if (RegSetValueEx(m_hKey,szValueName,NULL,(DWORD)REG_QWORD,(LPBYTE)&liValue, (DWORD)sizeof(__int64)) == ERROR_SUCCESS) { return true; } return false; } bool CRegistry::WriteString(const TCHAR *szValueName,TCHAR *szValue,unsigned long ulBufferSize) { if (RegSetValueEx(m_hKey,szValueName,NULL,REG_SZ,(LPBYTE)szValue,ulBufferSize) == ERROR_SUCCESS) return true; return false; } bool CRegistry::WriteStringEx(const TCHAR *szValueName,TCHAR *szValue) { unsigned long ulBufferSize = lstrlen(szValue); if (RegSetValueEx(m_hKey,szValueName,NULL,REG_SZ,(LPBYTE)szValue,ulBufferSize) == ERROR_SUCCESS) return true; return false; } ================================================ FILE: src/app/registry.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #define STRING_CHUNK_SIZE 128 class CRegistry { private: HKEY m_hRootKey; HKEY m_hKey; public: CRegistry(); ~CRegistry(); void SetRoot(HKEY hKey); bool OpenKey(const TCHAR *szKeyName,bool bCreate = true); bool CloseKey(); bool DeleteKey(const TCHAR *szKeyName); bool ReadBool(const TCHAR *szValueName,bool &bResult); bool ReadInteger(const TCHAR *szValueName,int &iResult); bool ReadInteger64(const TCHAR *szValueName,__int64 &iResult); bool ReadString(const TCHAR *szValueName,TCHAR *szResult,unsigned long ulBufferSize); bool ReadStringEx(const TCHAR *szValueName,TCHAR *&szResult); bool WriteBool(const TCHAR *szValueName,bool bValue); bool WriteInteger(const TCHAR *szValueName,int iValue); bool WriteInteger64(const TCHAR *szValueName,__int64 iValue); bool WriteString(const TCHAR *szValueName,TCHAR *szValue,unsigned long ulBufferSize); bool WriteStringEx(const TCHAR *szValueName,TCHAR *szValue); }; ================================================ FILE: src/app/resource.h ================================================ //{{NO_DEPENDENCIES}} // Microsoft Visual C++ generated include file. // Used by infrarecorder.rc // #define IDD_PROPPAGE_DEVICEGENERAL 106 #define IDR_MAINFRAME 128 #define ID_VIEW_UPLEVEL 129 #define ID_TRACK_READ 130 #define ID_TRACK_VERIFY 131 #define ID_TRACK_ERASE 132 #define ID_SHELLEXT_ADD 133 #define ID_SHELLEXT_REMOVE 134 #define ID_SHELL_PASTE 135 #define ID_BOOT_ADD 135 #define ID_BOOT_REMOVE 136 #define ID_BOOT_EDIT 137 #define IDR_MAINFRAME_PORTABLE 138 #define ID_NEWPROJECT_DATA 138 #define IDD_PROGRESSDLG 201 #define IDD_SIMPLEPROGRESSDLG 202 #define IDD_ERASEDLG 203 #define IDB_SPLASHBITMAP 204 #define IDD_LOGDLG 205 #define IDD_DEVICESDLG 206 #define IDD_PROPPAGE_DEVICEADVANCED 207 #define IDD_PROPPAGE_BURNIMAGEGENERAL 208 #define IDD_PROPPAGE_BURNIMAGEADVANCED 209 #define IDD_WAITDLG 210 #define IDI_MIXEDICON 211 #define IDD_PROPPAGE_PROJECTPROPGENERAL 211 #define IDI_AUDIOICON 212 #define IDD_PROPPAGE_PROJECTPROPISO 212 #define IDI_DATAICON 213 #define IDD_PROPPAGE_PROJECTPROPFIELDS 213 #define IDI_VIDEOICON 214 #define IDR_PROJLISTSELMENU 214 #define IDD_PROPPAGE_PROJECTPROPAUDIO 214 #define IDR_PROJLISTNOSELMENU 215 #define IDB_MINITOOLBARBITMAP 216 #define IDB_MINITOOLBARBITMAP_ 217 #define IDD_EDITTRACKDLG 218 #define IDD_FIXATEDLG 219 #define IDD_TRACKSDLG 220 #define IDD_PROPPAGE_CONFIGGENERAL 221 #define IDD_PROPPAGE_CONFIGADVANCED 222 #define IDB_TRACKTOOLBARBITMAP 223 #define IDD_PROPPAGE_CONFIGLANGUAGE 223 #define IDB_TRACKTOOLBARBITMAP_ 224 #define IDD_PROPPAGE_CONFIGSHELLEXT 224 #define IDD_NEWFILEEXTDLG 225 #define IDD_PROPPAGE_COPYDISCGENERAL 226 #define IDB_MAINSMALLBITMAP 228 #define IDB_MAINSMALLBITMAP_ 229 #define IDD_INFODLG 231 #define IDD_PROPPAGE_DISCGENERAL 232 #define IDD_IMPORTSESSIONDLG 233 #define IDI_PROJECTICON 238 #define IDD_SAVETRACKSDLG 239 #define IDD_PROPPAGE_READOPTIONS 240 #define IDD_PROPPAGE_COPYIMAGEGENERAL 241 #define IDD_PROPPAGE_PROJECTPROPBOOT 242 #define IDD_ADDBOOTIMAGEDLG 243 #define IDR_DIAGNOSTICSMENU 244 #define IDI_REFRESHICON 247 #define IDD_CONFIRMFILEREPLACEDLG 248 #define IDB_MAINLARGEBITMAP 249 #define IDD_PROPPAGE_PROJECTPROPFILESYS 249 #define IDB_MAINLARGEBITMAP_ 250 #define IDD_PROPPAGE_PROJECTPROPUDF 250 #define IDB_PANECLOSEBITMAP 251 #define IDB_BITMAP1 275 #define IDR_WELCOMELOGOPNG 278 #define IDR_BUTTONFPNG 279 #define IDR_BUTTONHPNG 280 #define IDR_BUTTONHFPNG 281 #define IDR_BUTTONNPNG 282 #define IDR_MBUTTONFPNG 283 #define IDR_MBUTTONHPNG 284 #define IDR_MBUTTONHFPNG 285 #define IDR_MBUTTONHFS1PNG 286 #define IDR_MBUTTONHFS2PNG 287 #define IDR_MBUTTONHS1PNG 288 #define IDR_MBUTTONHS2PNG 289 #define IDR_MBUTTONNPNG 290 #define IDR_WIZARDAUDIOPNG 291 #define IDR_WIZARDCOPYPNG 292 #define IDR_WIZARDDATAPNG 293 #define IDR_WIZARDREADPNG 294 #define IDR_WIZARDVIDEOPNG 295 #define IDR_WIZARDWRITEPNG 296 #define IDB_BITMAP2 297 #define IDB_ABOUTBITMAP 297 #define IDR_SHELLTREEMENU 298 #define IDC_TOTALPROGRESS 1000 #define IDC_TOTALSTATIC 1001 #define IDC_MESSAGELIST 1004 #define IDC_MESSAGESTATIC 1005 #define IDC_STATUSSTATIC 1005 #define IDC_BEVELSTATIC 1006 #define IDC_DEVICESTATIC 1007 #define IDC_BEVELSTATIC2 1007 #define IDC_BUFFERSTATIC 1008 #define IDC_BEVELSTATIC4 1008 #define IDC_BUFFERPROGRESS 1009 #define IDC_BEVELSTATIC3 1009 #define IDC_BEVELSTATIC5 1009 #define IDC_RECORDERSTATIC 1010 #define IDC_RECORDERCOMBO 1011 #define IDC_METHODSTATIC 1012 #define IDC_METHODCOMBO 1013 #define IDC_FORCECHECK 1014 #define IDC_EJECTCHECK 1015 #define IDC_SIMULATECHECK 1016 #define IDC_LOGEDIT 1017 #define IDC_BUTTON1 1018 #define IDC_RESCANBUTTON 1018 #define IDC_RELOADBUTTON 1018 #define IDC_BROWSEBUTTON 1018 #define IDC_DIAGNOSTICSBUTTON 1018 #define IDC_YESALLBUTTON 1018 #define ID_SAVEASBUTTON 1019 #define IDC_DEVICELIST 1020 #define IDC_INFOSTATIC 1021 #define IDC_ICONSTATIC 1022 #define IDC_NAMESTATIC 1023 #define IDC_OLDICONSTATIC 1023 #define IDC_TYPELABELSTATIC 1024 #define IDC_NEWICONSTATIC 1024 #define IDC_LOCATIONLABELSTATIC 1025 #define IDC_TYPESTATIC 1026 #define IDC_LOCATIONSTATIC 1027 #define IDC_BUFFERLABELSTATIC 1028 #define IDC_MAXREADLABELSTATIC 1029 #define IDC_MAXREADSTATIC 1030 #define IDC_MAXWRITELABELSTATIC 1031 #define IDC_MAXWRITESTATIC 1032 #define IDC_READSTATIC 1033 #define IDC_READCDRCHECK 1034 #define IDC_READDVDRAMCHECK 1035 #define IDC_READCDRWCHECK 1036 #define IDC_READDVDROMCHECK 1037 #define IDC_READDVDRCHECK 1038 #define IDC_WRITESTATIC 1039 #define IDC_WRITECDRCHECK 1040 #define IDC_WRITECDRWCHECK 1041 #define IDC_WRITEDVDRCHECK 1042 #define IDC_WRITEDVDRAMCHECK 1043 #define IDC_ADVLIST 1044 #define IDC_READDVDPLUSRCHECK 1044 #define IDC_READDVDPLUSRWCHECK 1045 #define IDC_WRITESPEEDSTATIC 1046 #define IDC_READDVDPLUSRDLCHECK 1046 #define IDC_WRITESPEEDCOMBO 1047 #define IDC_READDVDPLUSRWDLCHECK 1047 #define IDC_WRITEMETHODSTATIC 1048 #define IDC_READBDCHECK 1048 #define IDC_WRITEMETHODCOMBO 1049 #define IDC_READHDDVDCHECK 1049 #define IDC_WRITEDVDPLUSRCHECK 1050 #define IDC_WRITEDVDPLUSRWCHECK 1051 #define IDC_BUPCHECK 1052 #define IDC_WRITEDVDPLUSRDLCHECK 1052 #define IDC_PADCHECK 1053 #define IDC_WRITEDVDPLUSRWDLCHECK 1053 #define IDC_FIXATECHECK 1054 #define IDC_WRITEBDCHECK 1054 #define IDC_OVERBURNCHECK 1055 #define IDC_WRITEBDCHECK2 1055 #define IDC_WRITEHDDVDCHECK 1055 #define IDC_SWABCHECK 1056 #define IDC_IGNORESIZECHECK 1057 #define IDC_IMMEDCHECK 1058 #define IDC_AUDIOMASTERCHECK 1059 #define IDC_FORCESPEEDCHECK 1060 #define IDC_VARIRECCHECK 1061 #define IDC_VARIRECSLIDER 1062 #define IDC_VARIRECEDIT 1063 #define IDC_NAMEEDIT 1065 #define IDC_SIZELABELSTATIC 1066 #define IDC_CONTAINSLABELSTATIC 1067 #define IDC_SIZESTATIC 1068 #define IDC_CONTAINSSTATIC 1069 #define IDC_LEVELSTATIC 1070 #define IDC_LEVELCOMBO 1071 #define IDC_JOLIETCHECK 1074 #define IDC_JOLIETLONGNAMESCHECK 1075 #define IDC_PUBLISHEREDIT 1076 #define IDC_PUBLISHERSTATIC 1077 #define IDC_PREPAREREDIT 1078 #define IDC_SYSTEMEDIT 1079 #define IDC_VOLUMEEDIT 1080 #define IDC_PREPARERSTATIC 1081 #define IDC_SYSTEMSTATIC 1082 #define IDC_VOLUMESTATIC 1083 #define IDC_COPYRIGHTSTATIC 1084 #define IDC_COPYRIGHTEDIT 1085 #define IDC_ABSTRACTEDIT 1086 #define IDC_BIBLIOGRAPHICEDIT 1087 #define IDC_ABSTRACTSTATIC 1088 #define IDC_BIBLIOGRAPHICSTATIC 1089 #define IDC_FORMATCOMBO 1092 #define IDC_FORMATSTATIC 1093 #define IDC_ALBUMSTATIC 1094 #define IDC_CHARSETCOMBO 1094 #define IDC_ALBUMEDIT 1095 #define IDC_FORMATSTATIC2 1095 #define IDC_CHARSETSTATIC 1095 #define IDC_ARTISTEDIT 1096 #define IDC_ARTISTSTATIC 1097 #define IDC_TRACKLIST 1098 #define IDC_TITLESTATIC 1099 #define IDC_TITLEEDIT 1100 #define IDC_DEVICECOMBO 1103 #define IDC_DRIVESTATIC 1104 #define IDC_AUTORUNCHECK 1105 #define IDC_LOGCHECK 1106 #define IDC_TRACKCOMBO 1106 #define IDC_LANGUAGESTATIC 1107 #define IDC_LANGUAGECOMBO 1108 #define IDC_LANGUAGEINFOSTATIC 1109 #define IDC_SHELLEXTCHECK 1110 #define IDC_SHELLEXTSUBMENUCHECK 1111 #define IDC_SHELLEXTTEXTSTATIC 1112 #define IDC_SHELLEXTICONCHECK 1113 #define IDC_SHELLEXTLIST 1114 #define IDC_DESCSTATIC 1115 #define IDC_DESCEDIT 1116 #define IDC_EXTSTATIC 1117 #define IDC_EXTEDIT 1118 #define IDC_SOURCECOMBO 1119 #define IDC_SOURCESTATIC 1120 #define IDC_COMBO2 1121 #define IDC_TARGETCOMBO 1121 #define IDC_TARGETSTATIC 1122 #define IDC_IMAGESTATIC 1127 #define IDC_IMAGEEDIT 1128 #define IDC_ONFLYCHECK 1129 #define IDC_ONFLYSTATIC 1130 #define IDC_REMEMBERSHELLCHECK 1131 #define IDC_SHELLFOLDERGROUPSTATIC 1134 #define IDC_SHELLFOLDERINFOSTATIC 1135 #define IDC_SHELLFOLDEREDIT 1136 #define IDC_SHELLFOLDERBROWSEBUTTON 1137 #define IDC_DISPLAYMSGCHECK 1138 #define IDC_SHELLFOLDERBROWSEBUTTON2 1138 #define IDC_TEMPFOLDERBROWSEBUTTON 1138 #define IDC_BOOKLABELSTATIC 1139 #define IDC_BOOKSTATIC 1140 #define IDC_REGIONLABELSTATIC 1141 #define IDC_REGIONSTATIC 1142 #define IDC_LAYERLABELSTATIC 1143 #define IDC_LAYERSTATIC 1144 #define IDC_TRACKSTATIC 1145 #define IDC_TRACKLABELSTATIC 1146 #define IDC_SESSIONSTATIC 1147 #define IDC_SESSIONLABELSTATIC 1148 #define IDC_STATUSLABELSTATIC 1149 #define IDC_USEDSPACESTATIC 1150 #define IDC_USEDSPACELABELSTATIC 1151 #define IDC_FREESPACESTATIC 1152 #define IDC_FREESPACELABELSTATIC 1153 #define IDC_HELPBUTTON 1157 #define IDC_VERSIONSTATIC 1160 #define IDC_ASSOCIATECHECK 1161 #define IDC_CLONECHECK 1161 #define IDC_NOREADERRCHECK 1161 #define IDC_TEMPFOLDERGROUPSTATIC 1162 #define IDC_TEMPFOLDERINFOSTATIC 1163 #define IDC_TEMPFOLDEREDIT 1164 #define IDC_TARGETEDIT 1165 #define IDC_AUDIOFORMATSTATIC 1166 #define IDC_AUDIOFORMATCOMBO 1167 #define IDC_AUDIOFORMATBUTTON 1168 #define IDC_FIFOGROUPSTATIC 1171 #define IDC_FIFOINFOSTATIC 1172 #define IDC_FIFOEDIT 1173 #define IDC_FIFOMBSTATIC 1174 #define IDC_NOREADCORRCHECK 1175 #define IDC_SUBCHANNELCHECK 1176 #define IDC_READSUBCHANNELCHECK 1176 #define IDC_READSPEEDSTATIC 1177 #define IDC_READSPEEDCOMBO 1178 #define IDC_SPIN1 1179 #define IDC_BOOTSTATIC 1180 #define IDC_LIST 1181 #define IDC_BOOTCATALOGEDIT 1182 #define IDC_BOOTCATALOGSTATIC 1183 #define IDC_EMULATIONSTATIC 1185 #define IDC_EMULATIONCOMBO 1186 #define IDC_OPTIONSSTATIC 1187 #define IDC_NOBOOTCHECK 1188 #define IDC_BOOTINFOTABLECHECK 1189 #define IDC_BOOTSEGMENTEDIT 1190 #define IDC_BOOTSEGMENTSTATIC 1191 #define IDC_BOOTSIZEEDIT 1192 #define IDC_BOOTSIZESTATIC 1193 #define IDC_CHECK2 1196 #define IDC_CHECK 1196 #define IDC_OMITVNCHECK 1196 #define IDC_CHECK1 1197 #define IDC_VERIFYCHECK 1197 #define IDC_SMOKECHECK 1197 #define IDC_DEEPDIRCHECK 1197 #define IDC_DRIVELETTERCOMBO 1198 #define IDC_SPEEDCOMBO 1199 #define IDC_SPEEDSTATIC 1200 #define IDC_FILESBUTTON 1201 #define IDC_YESBUTTON 1202 #define IDC_NOBUTTON 1203 #define IDC_BUTTON2 1204 #define IDC_NOALLBUTTON 1204 #define IDC_REPLACEINFOSTATIC 1206 #define IDC_OLDSIZESTATIC 1207 #define IDC_OLDDATESTATIC 1208 #define IDC_REPLACEINFO2STATIC 1209 #define IDC_REFRESHBUTTON 1209 #define IDC_NEWSIZESTATIC 1210 #define IDC_FILESYSSTATIC 1210 #define IDC_NEWDATESTATIC 1211 #define IDC_FILESYSCOMBO 1211 #define IDC_VERSIONCOMBO 1212 #define IDC_PARTACCESSSTATIC 1214 #define IDC_ASSOCIATEDISCIMAGECHECK 1215 #define IDC_DATACDBUTTON 1220 #define IDC_DATADVDBUTTON 1221 #define IDC_IDC_WHITESTATIC 1223 #define IDC_WIZARDCHECK 1224 #define IDC_BUTTON3 1225 #define IDC_NUMCOPIESSTATIC 1226 #define IDC_NUMCOPIESCOMBO 1228 #define IDC_PROJECTTREEVIEW 10001 #define IDC_PROJECTLISTVIEW 10002 #define IDC_SHELLTREEVIEW 10003 #define IDC_SHELLLISTVIEW 10004 #define IDC_TBCUSTOMIZE_TEXTCOMBO 10005 #define IDC_TBCUSTOMIZE_ICONCOMBO 10006 #define ID_MENUROOT_FILE 11001 #define ID_MENUROOT_EDIT 11002 #define ID_MENUROOT_ACTIONS 11003 #define ID_MENUROOT_VIEW 11004 #define ID_MENUROOT_OPTIONS 11005 #define ID_MENUROOT_HELP 11006 #define ID_ACTIONS_ERASERE 32772 #define ID_ACTIONS_EJECT 32773 #define ID_EJECTDISC_ 32776 #define ID_VIEW_PROGRAMLOG 32778 #define ID_ACTIONS_BURNIMAGE 32780 #define ID_OPTIONS_CONFIGURATION 32781 #define ID_OPTIONS_DEVICES 32782 #define ID_FILE_NEWPROJECT 32783 #define ID_NEWPROJECT_DATACD 32784 #define ID_NEWPROJECT_AUDIO 32785 #define ID_NEWPROJECT_MIXED 32786 #define ID_EDIT_NEWFOLDER 32787 #define ID_Menu 32788 #define ID_EDIT_RENAME 32790 #define ID_EDIT_REMOVE 32791 #define ID_VIEW_LARGEICONS 32792 #define ID_VIEW_SMALLICONS 32793 #define ID_VIEW_LIST 32794 #define ID_VIEW_DETAILS 32795 #define ID_ACTIONS_BURNCOMPILATION 32800 #define ID_FILE_PROJECTPROPERTIES 32801 #define ID_BURNCOMPILATION_DISCIMAGE 32804 #define ID_BURNCOMPILATION_COMPACTDISC 32805 #define ID_ACTIONS_FIXATEDISC 32806 #define ID_ACTIONS_MANAGETRACKS 32807 #define ID_ACTIONS_COPYDISC 32808 #define ID_COPYDISC_COMPACTDISC 32811 #define ID_COPYDISC_DISCIMAGE 32812 #define ID_EDIT_ADDPROJECT 32814 #define ID_ADD_SELECTED 32818 #define ID_ADD_ALL 32819 #define ID_ACTIONS_DISCINFORMATION 32821 #define ID_ACTIONS_IMPORTSESSION 32822 #define ID_DISCINFORMATION_ 32823 #define ID_HELP_HELPTOPICS 32824 #define ID_NEWPROJECT_DVDVIDEO 32826 #define ID_NEWPROJECT_DATADVD 32827 #define ID__DEVICESCAN 32828 #define ID__DIAGNOSTICS_DEVICESCAN 32829 #define ID_DIAGNOSTICS_DEVICESCAN 32830 #define ID_VIEW_TOOLBARS 32831 #define ID_TOOLBARS_STANDARDBUTTONS 32832 #define ID_TOOLBARS_CUSTOMIZE 32833 #define ID_VIEW_STANDARDTOOLBAR 32834 #define ID_VIEW_TBCUSTOMIZE 32835 #define ID_EDIT_SELECTALL 32836 #define ID_EDIT_INVERTSELECTION 32837 #define ID_POPUPMENU_PROPERTIES 32840 #define ID_NEWPROJECT_DATACD32841 32841 #define ID_NEWPROJECT_DATACDMS 32842 #define ID_EDIT_IMPORT 32843 #define ID_POPUPMENU_SHELLTREE_PROPERTIES 32844 // Next default values for new objects // #ifdef APSTUDIO_INVOKED #ifndef APSTUDIO_READONLY_SYMBOLS #define _APS_NEXT_RESOURCE_VALUE 298 #define _APS_NEXT_COMMAND_VALUE 32845 #define _APS_NEXT_CONTROL_VALUE 1229 #define _APS_NEXT_SYMED_VALUE 101 #endif #endif ================================================ FILE: src/app/settings.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "main_frm.hh" #include "toolbar_manager.hh" #include "settings.hh" CLanguageSettings g_LanguageSettings; CGlobalSettings g_GlobalSettings; CDynamicSettings g_DynamicSettings; CEraseSettings g_EraseSettings; CFixateSettings g_FixateSettings; CBurnImageSettings g_BurnImageSettings; CProjectSettings g_ProjectSettings; CCopyDiscSettings g_CopyDiscSettings; CBurnAdvancedSettings g_BurnAdvancedSettings; CSaveTracksSettings g_SaveTracksSettings; CReadSettings g_ReadSettings; bool CLanguageSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("Language"),_T(""),true); pXml->AddElement(_T("LanguageFile"),m_szLanguageFile); pXml->LeaveElement(); return true; } bool CLanguageSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("Language"))) return false; pXml->GetSafeElementData(_T("LanguageFile"),m_szLanguageFile,MAX_PATH - 1); // Calculate full path. TCHAR szFullPath[MAX_PATH]; ::GetModuleFileName(NULL,szFullPath,MAX_PATH - 1); ExtractFilePath(szFullPath); lstrcat(szFullPath,_T("languages\\")); lstrcat(szFullPath,m_szLanguageFile); if (ckcore::File::exist(szFullPath)) { m_pLngProcessor = new CLngProcessor(szFullPath); m_pLngProcessor->Load(); } pXml->LeaveElement(); return true; } bool CGlobalSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("Global"),_T(""),true); pXml->AddElement(_T("AutoRunCheck"),m_bAutoRunCheck); pXml->AddElement(_T("Log"),m_bLog); pXml->AddElement(_T("RememberShell"),m_bRememberShell); pXml->AddElement(_T("CopyWarning"),m_bCopyWarning); pXml->AddElement(_T("RawImageInfo"),m_bRawImageInfo); pXml->AddElement(_T("CharSetWarning"),m_bCharSetWarning); pXml->AddElement(_T("WriteSpeedWarning"),m_bWriteSpeedWarning); pXml->AddElement(_T("CodecWarning"),m_bCodecWarning); pXml->AddElement(_T("FixateWarning"),m_bFixateWarning); pXml->AddElement(_T("NoDevWarning"),m_bNoDevWarning); pXml->AddElement(_T("Smoke"),m_bSmoke); pXml->AddElement(_T("Wizard"),m_bShowWizard); pXml->AddElement(_T("GraceTime"),m_iGraceTime); pXml->AddElement(_T("FIFO"),m_iFIFOSize); if (m_iFIFOSize > FIFO_MAX) m_iFIFOSize = FIFO_MAX; else if (m_iFIFOSize < FIFO_MIN) m_iFIFOSize = FIFO_MIN; // Temporary folder. pXml->AddElement(_T("TempPath"),m_szTempPath); // Shell extension. pXml->AddElement(_T("ShellExtension"),_T(""),true); pXml->AddElementAttr(_T("submenu"),m_bShellExtSubMenu); pXml->AddElementAttr(_T("icons"),m_bShellExtIcon); pXml->AddElementAttr(_T("count"),(int)m_szShellExt.size()); TCHAR szItemName[32]; int iItemCount = 0; std::list::iterator itNodeObject; for (itNodeObject = m_szShellExt.begin(); itNodeObject != m_szShellExt.end(); itNodeObject++) { lsprintf(szItemName,_T("Item%i"),iItemCount++); pXml->AddElement(szItemName,(*itNodeObject).c_str()); } pXml->LeaveElement(); pXml->LeaveElement(); return true; } bool CGlobalSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("Global"))) return false; pXml->GetSafeElementData(_T("AutoRunCheck"),&m_bAutoRunCheck); pXml->GetSafeElementData(_T("Log"),&m_bLog); pXml->GetSafeElementData(_T("RememberShell"),&m_bRememberShell); pXml->GetSafeElementData(_T("CopyWarning"),&m_bCopyWarning); pXml->GetSafeElementData(_T("RawImageInfo"),&m_bRawImageInfo); pXml->GetSafeElementData(_T("CharSetWarning"),&m_bCharSetWarning); pXml->GetSafeElementData(_T("WriteSpeedWarning"),&m_bWriteSpeedWarning); pXml->GetSafeElementData(_T("CodecWarning"),&m_bCodecWarning); pXml->GetSafeElementData(_T("FixateWarning"),&m_bFixateWarning); pXml->GetSafeElementData(_T("NoDevWarning"),&m_bNoDevWarning); pXml->GetSafeElementData(_T("Smoke"),&m_bSmoke); pXml->GetSafeElementData(_T("Wizard"),&m_bShowWizard); pXml->GetSafeElementData(_T("GraceTime"),&m_iGraceTime); pXml->GetSafeElementData(_T("FIFO"),&m_iFIFOSize); // Temporary folder. pXml->GetSafeElementData(_T("TempPath"),m_szTempPath,MAX_PATH - 1); if (!ckcore::Directory::exist(m_szTempPath)) { // If the folder does not exist, create it. if (m_szTempPath == NULL || lstrlen(m_szTempPath) < 3 || m_szTempPath[1] != ':') { IncludeTrailingBackslash(m_szTempPath); ckcore::Directory::create(m_szTempPath); } else { GetTempPath(MAX_PATH - 1,m_szTempPath); } } // Shell extension. if (pXml->EnterElement(_T("ShellExtension"))) { pXml->GetSafeElementAttrValue(_T("submenu"),&m_bShellExtSubMenu); pXml->GetSafeElementAttrValue(_T("icons"),&m_bShellExtIcon); int iItemCount = 0; TCHAR szItemName[32]; TCHAR szBuffer[128]; pXml->GetSafeElementAttrValue(_T("count"),&iItemCount); m_szShellExt.clear(); for (int i = 0; i < iItemCount; i++) { lsprintf(szItemName,_T("Item%i"),i); pXml->GetSafeElementData(szItemName,szBuffer,127); m_szShellExt.push_back(szBuffer); } pXml->LeaveElement(); } pXml->LeaveElement(); return true; } bool CDynamicSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("Dynamic"),_T(""),true); pXml->AddElement(_T("ProjectListViewStyle"),m_iPrjListViewStyle); pXml->AddElement(_T("ToolBar"),m_bViewToolBar,true); pXml->AddElementAttr(_T("text"),m_iToolBarText); pXml->AddElementAttr(_T("icon"),m_iToolBarIcon); pXml->LeaveElement(); pXml->AddElement(_T("StatusBar"),m_bViewStatusBar); pXml->AddElement(_T("WindowLeft"),m_rcWindow.left); pXml->AddElement(_T("WindowRight"),m_rcWindow.right); pXml->AddElement(_T("WindowTop"),m_rcWindow.top); pXml->AddElement(_T("WindowBottom"),m_rcWindow.bottom); pXml->AddElement(_T("WindowMaximized"),m_bWinMaximized); pXml->AddElement(_T("ShellDir"),m_szShellDir); // Save the toolbar button configuration. g_ToolBarManager.Save(pXml); pXml->LeaveElement(); return true; } bool CDynamicSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("Dynamic"))) return false; pXml->GetSafeElementData(_T("ProjectListViewStyle"),&m_iPrjListViewStyle); if (pXml->EnterElement(_T("ToolBar"))) { pXml->GetSafeElementData(&m_bViewToolBar); pXml->GetSafeElementAttrValue(_T("text"),&m_iToolBarText); pXml->GetSafeElementAttrValue(_T("icon"),&m_iToolBarIcon); pXml->LeaveElement(); // Validate the values. if (m_iToolBarText > TOOLBAR_TEXT_DONTSHOW || m_iToolBarText < 0) m_iToolBarText = TOOLBAR_TEXT_DONTSHOW; if (m_iToolBarIcon > TOOLBAR_ICON_LARGE || m_iToolBarIcon < 0) m_iToolBarIcon = TOOLBAR_ICON_SMALL; } pXml->GetSafeElementData(_T("StatusBar"),&m_bViewStatusBar); pXml->GetSafeElementData(_T("WindowLeft"),&m_rcWindow.left); pXml->GetSafeElementData(_T("WindowRight"),&m_rcWindow.right); pXml->GetSafeElementData(_T("WindowTop"),&m_rcWindow.top); pXml->GetSafeElementData(_T("WindowBottom"),&m_rcWindow.bottom); pXml->GetSafeElementData(_T("WindowMaximized"),&m_bWinMaximized); pXml->GetSafeElementData(_T("ShellDir"),m_szShellDir,MAX_PATH - 1); // Save the toolbar button configuration. g_ToolBarManager.Load(pXml); pXml->LeaveElement(); return true; } void CDynamicSettings::Apply() { // Apply the project list view style. switch (m_iPrjListViewStyle) { case LISTVIEWSTYLE_LARGEICONS: CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_LARGEICONS,MF_BYCOMMAND | MF_CHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_SMALLICONS,MF_BYCOMMAND | MF_UNCHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_LIST,MF_BYCOMMAND | MF_UNCHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_DETAILS,MF_BYCOMMAND | MF_UNCHECKED); g_pMainFrame->UISetCheck(ID_VIEW_LARGEICONS,true); g_pMainFrame->UISetCheck(ID_VIEW_SMALLICONS,false); g_pMainFrame->UISetCheck(ID_VIEW_LIST,false); g_pMainFrame->UISetCheck(ID_VIEW_DETAILS,false); break; case LISTVIEWSTYLE_SMALLICONS: CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_LARGEICONS,MF_BYCOMMAND | MF_UNCHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_SMALLICONS,MF_BYCOMMAND | MF_CHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_LIST,MF_BYCOMMAND | MF_UNCHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_DETAILS,MF_BYCOMMAND | MF_UNCHECKED); g_pMainFrame->UISetCheck(ID_VIEW_LARGEICONS,false); g_pMainFrame->UISetCheck(ID_VIEW_SMALLICONS,true); g_pMainFrame->UISetCheck(ID_VIEW_LIST,false); g_pMainFrame->UISetCheck(ID_VIEW_DETAILS,false); break; case LISTVIEWSTYLE_LIST: CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_LARGEICONS,MF_BYCOMMAND | MF_UNCHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_SMALLICONS,MF_BYCOMMAND | MF_UNCHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_LIST,MF_BYCOMMAND | MF_CHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_DETAILS,MF_BYCOMMAND | MF_UNCHECKED); g_pMainFrame->UISetCheck(ID_VIEW_LARGEICONS,false); g_pMainFrame->UISetCheck(ID_VIEW_SMALLICONS,false); g_pMainFrame->UISetCheck(ID_VIEW_LIST,true); g_pMainFrame->UISetCheck(ID_VIEW_DETAILS,false); break; case LISTVIEWSTYLE_DETAILS: CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_LARGEICONS,MF_BYCOMMAND | MF_UNCHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_SMALLICONS,MF_BYCOMMAND | MF_UNCHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_LIST,MF_BYCOMMAND | MF_UNCHECKED); CheckMenuItem(g_pMainFrame->m_hProjListNoSelMenu,ID_VIEW_DETAILS,MF_BYCOMMAND | MF_CHECKED); g_pMainFrame->UISetCheck(ID_VIEW_LARGEICONS,false); g_pMainFrame->UISetCheck(ID_VIEW_SMALLICONS,false); g_pMainFrame->UISetCheck(ID_VIEW_LIST,false); g_pMainFrame->UISetCheck(ID_VIEW_DETAILS,true); break; }; g_pMainFrame->m_ProjectListView.SetViewStyle(m_iPrjListViewStyle); } bool CEraseSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("Erase"),_T(""),true); pXml->AddElement(_T("Mode"),m_iMode); pXml->AddElement(_T("Force"),m_bForce); pXml->AddElement(_T("Eject"),m_bEject); pXml->AddElement(_T("Simulate"),m_bSimulate); pXml->LeaveElement(); return true; } bool CEraseSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("Erase"))) return false; pXml->GetSafeElementData(_T("Mode"),&m_iMode); pXml->GetSafeElementData(_T("Force"),&m_bForce); pXml->GetSafeElementData(_T("Eject"),&m_bEject); pXml->GetSafeElementData(_T("Simulate"),&m_bSimulate); pXml->LeaveElement(); return true; } bool CFixateSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("Fixate"),_T(""),true); pXml->AddElement(_T("Eject"),m_bEject); pXml->AddElement(_T("Simulate"),m_bSimulate); pXml->LeaveElement(); return true; } bool CFixateSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("Fixate"))) return false; pXml->GetSafeElementData(_T("Eject"),&m_bEject); pXml->GetSafeElementData(_T("Simulate"),&m_bSimulate); pXml->LeaveElement(); return true; } bool CBurnImageSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("BurnImage"),_T(""),true); pXml->AddElement(_T("OnFly"),m_bOnFly); pXml->AddElement(_T("Verify"),m_bVerify); pXml->AddElement(_T("Eject"),m_bEject); pXml->AddElement(_T("Simulate"),m_bSimulate); pXml->AddElement(_T("BUP"),m_bBUP); pXml->AddElement(_T("PadTracks"),m_bPadTracks); pXml->AddElement(_T("Fixate"),m_bFixate); pXml->LeaveElement(); return true; } bool CBurnImageSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("BurnImage"))) return false; pXml->GetSafeElementData(_T("OnFly"),&m_bOnFly); pXml->GetSafeElementData(_T("Verify"),&m_bVerify); pXml->GetSafeElementData(_T("Eject"),&m_bEject); pXml->GetSafeElementData(_T("Simulate"),&m_bSimulate); pXml->GetSafeElementData(_T("BUP"),&m_bBUP); pXml->GetSafeElementData(_T("PadTracks"),&m_bPadTracks); pXml->GetSafeElementData(_T("Fixate"),&m_bFixate); pXml->LeaveElement(); return true; } bool CProjectSettings::Save(CXmlProcessor *pXml) { return false; } bool CProjectSettings::Load(CXmlProcessor *pXml) { return false; } bool CCopyDiscSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("CopyDisc"),_T(""),true); pXml->AddElement(_T("OnFly"),m_bOnFly); pXml->AddElement(_T("Clone"),m_bClone); pXml->LeaveElement(); return true; } bool CCopyDiscSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("CopyDisc"))) return false; pXml->GetSafeElementData(_T("OnFly"),&m_bOnFly); pXml->GetSafeElementData(_T("Clone"),&m_bClone); pXml->LeaveElement(); return true; } bool CBurnAdvancedSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("BurnAdvanced"),_T(""),true); pXml->AddElement(_T("Overburn"),m_bOverburn); pXml->AddElement(_T("Swab"),m_bSwab); pXml->AddElement(_T("IgnoreSize"),m_bIgnoreSize); pXml->AddElement(_T("Immed"),m_bImmed); pXml->AddElement(_T("AudioMaster"),m_bAudioMaster); pXml->AddElement(_T("ForceSpeed"),m_bForceSpeed); pXml->AddElement(_T("VariRec"),m_bVariRec,true); pXml->AddElementAttr(_T("value"),m_iVariRec); pXml->LeaveElement(); pXml->LeaveElement(); return true; } bool CBurnAdvancedSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("BurnAdvanced"))) return false; pXml->GetSafeElementData(_T("Overburn"),&m_bOverburn); pXml->GetSafeElementData(_T("Swab"),&m_bSwab); pXml->GetSafeElementData(_T("IgnoreSize"),&m_bIgnoreSize); pXml->GetSafeElementData(_T("Immed"),&m_bImmed); pXml->GetSafeElementData(_T("AudioMaster"),&m_bAudioMaster); pXml->GetSafeElementData(_T("ForceSpeed"),&m_bForceSpeed); if (pXml->EnterElement(_T("VariRec"))) { pXml->GetSafeElementData(&m_bVariRec); pXml->GetSafeElementAttrValue(_T("value"),&m_iVariRec); pXml->LeaveElement(); } pXml->LeaveElement(); return true; } bool CSaveTracksSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("SaveTracks"),_T(""),true); pXml->AddElement(_T("Target"),m_szTarget); pXml->LeaveElement(); return true; } bool CSaveTracksSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("SaveTracks"))) return false; pXml->GetSafeElementData(_T("Target"),m_szTarget,MAX_PATH - 1); pXml->LeaveElement(); return true; } bool CReadSettings::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("Read"),_T(""),true); pXml->AddElement(_T("IgnoreErr"),m_bIgnoreErr); pXml->AddElement(_T("Clone"),m_bClone); pXml->LeaveElement(); return true; } bool CReadSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("Read"))) return false; pXml->GetSafeElementData(_T("IgnoreErr"),&m_bIgnoreErr); pXml->GetSafeElementData(_T("Clone"),&m_bClone); pXml->LeaveElement(); return true; } ================================================ FILE: src/app/settings.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include #include #include #include "tree_manager.hh" #define WRITEMETHOD_SAO 0 #define WRITEMETHOD_TAO 1 #define WRITEMETHOD_TAONOPREGAP 2 #define WRITEMETHOD_RAW96R 3 #define WRITEMETHOD_RAW16 4 #define WRITEMETHOD_RAW96P 5 #define LISTVIEWSTYLE_LARGEICONS 0 #define LISTVIEWSTYLE_SMALLICONS 1 #define LISTVIEWSTYLE_LIST 2 #define LISTVIEWSTYLE_DETAILS 3 #define TOOLBAR_TEXT_SHOW 0 #define TOOLBAR_TEXT_SHOWRIGHT 1 #define TOOLBAR_TEXT_DONTSHOW 2 #define TOOLBAR_ICON_SMALL 0 #define TOOLBAR_ICON_LARGE 1 // FIFO_MAX was previously set to 128 MiB, which I found to be too low nowadays. // Just think of the 4.7 GiB on a DVD, or the upcoming 25 GiB on a Blu-ray, // those devices can write 128 MiB in a few of seconds. However, // the hardware buffers on the recorders are still ridiculously small, // and I don't like constantly relying on the standard hardware buffer underrun protection // (BURN-Proof, SafeBurn and so on), because they tend to cause small errors and // they hope that the error correction will compensate. // // There seems to be some FIFO size limit in cdrecord (version 2.01.01a61 under Cygwin, // bundled with InfraRecorder 0.50 as of Sept 2009), but it's not well documented. // I've done some tests under Windows XP & Vista, and 850 MiB seems to be fine, but 900 MiB fails. // The chosen 800 MiB limit is just some arbitrary number below those figures. // This is the error message you get if you set it too high: // [...]/binary32/cdrtools/cdrecord: Cannot allocate memory. Cannot get mmap for 1047592960 Bytes on /dev/zero. // It seems strange that cdrecord needs to mmap /dev/zero for that purpose, but maybe that'll // change in the future. #define FIFO_MAX 800 // In MiB. #define FIFO_MIN 4 #define FILESYSTEM_ISO 0 #define FILESYSTEM_ISO_UDF 1 #define FILESYSTEM_DVDVIDEO 2 #define FILESYSTEM_UDF 3 class ISettings { public: virtual bool Save(CXmlProcessor *pXml) = 0; virtual bool Load(CXmlProcessor *pXml) = 0; }; class CLanguageSettings : public ISettings { public: TCHAR m_szLanguageFile[MAX_PATH]; CLngProcessor *m_pLngProcessor; CLanguageSettings() { m_szLanguageFile[0] = '\0'; m_pLngProcessor = NULL; } ~CLanguageSettings() { if (m_pLngProcessor != NULL) { delete m_pLngProcessor; m_pLngProcessor = NULL; } } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; class CGlobalSettings : public ISettings { public: bool m_bAutoRunCheck; bool m_bLog; bool m_bRememberShell; bool m_bCopyWarning; // Display the warning message about audio discs when trying to copy a disc. bool m_bRawImageInfo; // Display information about raw write methods when writing a "raw" disc image. bool m_bCharSetWarning; // Display the warning if the character set could not be recognized. bool m_bWriteSpeedWarning; // Display a warning when changing the write speed of a recorder. bool m_bCodecWarning; // Display a warning when a codec failed to load. bool m_bFixateWarning; // Display a warning when trying to disable disc fixation. bool m_bNoDevWarning; // Display a warning when no devices are found in the system. bool m_bSmoke; bool m_bShowWizard; int m_iGraceTime; int m_iFIFOSize; TCHAR m_szTempPath[MAX_PATH]; // Shell extension. bool m_bShellExtSubMenu; bool m_bShellExtIcon; std::list m_szShellExt; // For internal use only (at this moment). TCHAR m_szCDRToolsPath[MAX_PATH]; TCHAR m_szCDRToolsPathCyg[MAX_PATH + 12]; CGlobalSettings() { m_bAutoRunCheck = true; m_bLog = true; m_bRememberShell = true; m_bCopyWarning = true; m_bRawImageInfo = true; m_bCharSetWarning = true; m_bWriteSpeedWarning = true; m_bCodecWarning = true; m_bFixateWarning = true; m_bNoDevWarning = true; m_bSmoke = true; m_bShowWizard = true; m_iGraceTime = 5; // Five seconds by default. m_iFIFOSize = 4; // 4 MiB by default. // Path to system temporary directory. m_szTempPath[0] = '\0'; GetTempPath(MAX_PATH - 1,m_szTempPath); // Shell extension. m_bShellExtSubMenu = false; m_bShellExtIcon = true; m_szShellExt.push_back(_T("Disc Images|.iso, .cue")); m_szShellExt.push_back(_T("Raw Images|.bin, .raw")); m_szShellExt.push_back(_T("InfraRecorder Projects|.irp")); // Path to cdrtools. GetModuleFileName(NULL,m_szCDRToolsPath,MAX_PATH - 1); ExtractFilePath(m_szCDRToolsPath); #ifdef CDRKIT lstrcat(m_szCDRToolsPath,_T("cdrkit\\")); #else lstrcat(m_szCDRToolsPath,_T("cdrtools\\")); #endif // Cygwin version of the path. GetCygwinFileName(m_szCDRToolsPath,m_szCDRToolsPathCyg); } ~CGlobalSettings() { // Shell extension. m_szShellExt.clear(); } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; class CDynamicSettings : public ISettings { public: int m_iPrjListViewStyle; int m_iToolBarText; int m_iToolBarIcon; bool m_bViewToolBar; bool m_bViewStatusBar; bool m_bWinMaximized; // Window rectangle. RECT m_rcWindow; // Contains the active path displayed in the explorer view. TCHAR m_szShellDir[MAX_PATH]; CDynamicSettings() { m_iPrjListViewStyle = LISTVIEWSTYLE_DETAILS; m_iToolBarText = TOOLBAR_TEXT_DONTSHOW; m_iToolBarIcon = TOOLBAR_ICON_SMALL; m_bViewToolBar = true; m_bViewStatusBar = true; m_bWinMaximized = false; // -1 means not set. m_rcWindow.left = -1; m_rcWindow.right = -1; m_rcWindow.top = -1; m_rcWindow.bottom = -1; // The default shell path should be the desktop. if (!SHGetSpecialFolderPath(NULL,m_szShellDir,CSIDL_DESKTOP,false)) m_szShellDir[0] = '\0'; } ~CDynamicSettings() { } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); void Apply(); }; class CEraseSettings : public ISettings { public: int m_iMode; bool m_bForce; bool m_bEject; bool m_bSimulate; // For internal use only, should never be saved. ckmmc::Device *m_pRecorder; unsigned int m_uiSpeed; CEraseSettings() { m_iMode = 1; m_bForce = false; m_bEject = true; m_bSimulate = false; m_pRecorder = NULL; m_uiSpeed = 0xFFFFFFFF; // Maximum. } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; class CFixateSettings : public ISettings { public: bool m_bEject; bool m_bSimulate; // For internal use only, should never be saved. ckmmc::Device *m_pRecorder; CFixateSettings() { m_bEject = true; m_bSimulate = false; m_pRecorder = NULL; } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; class CBurnImageSettings : public ISettings { public: bool m_bOnFly; bool m_bVerify; bool m_bEject; bool m_bSimulate; bool m_bBUP; bool m_bPadTracks; bool m_bFixate; // For internal use only, should never be saved. ckmmc::Device *m_pRecorder; int m_iWriteMethod; int m_iWriteSpeed; // Multiple of what has been defined as single speed for the current medium, -1 for maximum speed. long m_lNumCopies; CBurnImageSettings() { m_bOnFly = false; m_bVerify = false; m_bEject = true; m_bSimulate = false; m_bBUP = true; m_bPadTracks = true; m_bFixate = true; m_pRecorder = NULL; m_iWriteMethod = 0; m_iWriteSpeed = -1; // For internal use only, should never be saved. m_pRecorder= NULL; m_lNumCopies = 1; } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; // Class used to destribe a project boot image. #define PROJECTBI_BOOTEMU_NONE 0 #define PROJECTBI_BOOTEMU_FLOPPY 1 #define PROJECTBI_BOOTEMU_HARDDISK 2 class CProjectBootImage // FIXME: Make m_iLoadSegment and m_iLoadSize unsigned short, m_iEmulation to enum type and m_iLoadSize to LoadLen (sectors). { public: bool m_bNoBoot; int m_iEmulation; ckcore::tuint16 m_uiLoadSegment; ckcore::tuint16 m_uiLoadSize; ckcore::tstring m_FullPath; // Full path to the file on the harddrive. ckcore::tstring m_LocalName; // Internal name. CProjectBootImage() { m_bNoBoot = false; m_iEmulation = PROJECTBI_BOOTEMU_FLOPPY; m_uiLoadSegment = 0x7c0; m_uiLoadSize = 4; } }; class CProjectSettings : public ISettings { public: int m_iFileSystem; int m_iIsoLevel; int m_iIsoFormat; // FIXME: Use defined values here. Rename? enum IsoCharSet { CHARSET_ISO, CHARSET_DOS, CHARSET_ASCII } m_IsoCharSet; bool m_bJoliet; bool m_bJolietLongNames; bool m_bOmitVerNum; bool m_bDeepDirs; TCHAR m_szLabel[128]; TCHAR m_szPublisher[128]; TCHAR m_szPreparer[128]; TCHAR m_szSystem[128]; TCHAR m_szVolumeSet[128]; TCHAR m_szCopyright[37]; TCHAR m_szAbstract[37]; TCHAR m_szBibliographic[37]; TCHAR m_szAlbumName[160]; TCHAR m_szAlbumArtist[160]; // Boot information. std::list m_BootImages; // Multi session related, are only changed when importing an existing session. // They should not be saved in a project. bool m_bMultiSession; unsigned __int64 m_uiImportTrackAddr; unsigned __int64 m_uiImportTrackLen; unsigned __int64 m_uiNextWritableAddr; ckmmc::Device *m_pDevice; CProjectSettings() { // We don't want to display an error message if the code page is not // found two times. First when the object enters scope and later when // the new project is created (from the NewDataProject function). Reset(); } ~CProjectSettings() { // Free any boot image information. std::list ::iterator itImageObject; for (itImageObject = m_BootImages.begin(); itImageObject != m_BootImages.end(); itImageObject++) delete *itImageObject; m_BootImages.clear(); } /* CProjectSettings::GetBootImage ------------------------------ Returns the CProjectBootImage object that is associated with the specified file name (full local file name of a file on the hard disk). */ CProjectBootImage *GetBootImage(const TCHAR *szFileName) { std::list ::iterator itImageObject; for (itImageObject = m_BootImages.begin(); itImageObject != m_BootImages.end(); itImageObject++) { if (!ComparePaths((*itImageObject)->m_FullPath.c_str(),szFileName)) return *itImageObject; } return NULL; } void Reset() { m_iFileSystem = FILESYSTEM_ISO; m_iIsoLevel = 2; m_iIsoFormat = 0; m_iIsoFormat = CHARSET_ISO; m_bJoliet = true; m_bJolietLongNames = true; m_bOmitVerNum = false; m_bDeepDirs = true; m_szLabel[0] = '\0'; m_szPublisher[0] = '\0'; m_szPreparer[0] = '\0'; m_szSystem[0] = '\0'; m_szVolumeSet[0] = '\0'; m_szCopyright[0] = '\0'; m_szAbstract[0] = '\0'; m_szBibliographic[0] = '\0'; m_szAlbumName[0] = '\0'; m_szAlbumArtist[0] = '\0'; std::list ::iterator itImageObject; for (itImageObject = m_BootImages.begin(); itImageObject != m_BootImages.end(); itImageObject++) delete *itImageObject; m_BootImages.clear(); // Multi session related, are only changed when importing an existing session. m_bMultiSession = false; m_uiImportTrackAddr = 0; m_uiImportTrackLen = 0; m_uiNextWritableAddr = 0; m_pDevice = NULL; } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; class CCopyDiscSettings : public ISettings { public: bool m_bOnFly; bool m_bClone; // For internal use only, should never be saved. ckmmc::Device *m_pSource; ckmmc::Device *m_pTarget; // Size of the source drive media in sectors. unsigned __int64 m_uiSourceSize; CCopyDiscSettings() { m_bOnFly = false; m_bClone = true; m_pSource = NULL; m_pTarget = NULL; m_uiSourceSize = 0; } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; class CBurnAdvancedSettings : public ISettings { public: bool m_bOverburn; bool m_bSwab; bool m_bIgnoreSize; bool m_bImmed; bool m_bAudioMaster; bool m_bForceSpeed; bool m_bVariRec; int m_iVariRec; CBurnAdvancedSettings() { m_bOverburn = false; m_bSwab = false; m_bIgnoreSize = false; m_bImmed = false; m_bAudioMaster = true; m_bForceSpeed = false; m_bVariRec = false; m_iVariRec = 0; } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; class CSaveTracksSettings : public ISettings { public: TCHAR m_szTarget[MAX_PATH]; CSaveTracksSettings() { m_szTarget[0] = '\0'; } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; class CReadSettings : public ISettings { public: bool m_bIgnoreErr; bool m_bClone; // For internal use only, should never be saved. INT_PTR m_iReadSpeed; // Read speed (audio multiple). CReadSettings() { m_bIgnoreErr = false; m_bClone = false; m_iReadSpeed = -1; // -1 = Maximum. } bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); }; extern CLanguageSettings g_LanguageSettings; extern CGlobalSettings g_GlobalSettings; extern CDynamicSettings g_DynamicSettings; extern CEraseSettings g_EraseSettings; extern CFixateSettings g_FixateSettings; extern CBurnImageSettings g_BurnImageSettings; extern CProjectSettings g_ProjectSettings; extern CCopyDiscSettings g_CopyDiscSettings; extern CBurnAdvancedSettings g_BurnAdvancedSettings; extern CSaveTracksSettings g_SaveTracksSettings; extern CReadSettings g_ReadSettings; ================================================ FILE: src/app/settings_manager.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include #include "settings_manager.hh" #include "string_table.hh" #include "lang_util.hh" CSettingsManager g_SettingsManager; CSettingsManager::CSettingsManager() { RegisterObject(&g_LanguageSettings); RegisterObject(&g_GlobalSettings); RegisterObject(&g_DynamicSettings); RegisterObject(&g_EraseSettings); RegisterObject(&g_FixateSettings); RegisterObject(&g_BurnImageSettings); RegisterObject(&g_CopyDiscSettings); RegisterObject(&g_BurnAdvancedSettings); RegisterObject(&g_SaveTracksSettings); RegisterObject(&g_ReadSettings); } CSettingsManager::~CSettingsManager() { m_Settings.clear(); } void CSettingsManager::RegisterObject(ISettings *pSettings) { m_Settings.push_back(pSettings); } bool CSettingsManager::GetConfigPath(TCHAR *szConfigPath) { #ifdef PORTABLE GetModuleFileName(NULL,szConfigPath,MAX_PATH - 1); ExtractFilePath(szConfigPath); #else if (!SUCCEEDED(SHGetFolderPath(HWND_DESKTOP,CSIDL_APPDATA | CSIDL_FLAG_CREATE,NULL, SHGFP_TYPE_CURRENT,szConfigPath))) return false; IncludeTrailingBackslash(szConfigPath); lstrcat(szConfigPath,_T("InfraRecorder\\")); // Create the file path if it doesn't exist. ckcore::Directory::create(szConfigPath); #endif lstrcat(szConfigPath,_T("settings.xml")); return true; } bool CSettingsManager::Save() { CXmlProcessor Xml; bool bResult = true; Xml.AddElement(_T("InfraRecorder"),_T(""),true); Xml.AddElement(_T("Settings"),_T(""),true); for (unsigned int i = 0; i < m_Settings.size(); i++) { if (!m_Settings[i]->Save(&Xml)) bResult = false; } Xml.LeaveElement(); Xml.LeaveElement(); // Get the correct file-path. TCHAR szConfigPath[MAX_PATH]; if (!GetConfigPath(szConfigPath)) return false; return bResult && Xml.Save(szConfigPath); } bool CSettingsManager::Load() { CXmlProcessor Xml; bool bResult = true; // Get the correct file-path. TCHAR szConfigPath[MAX_PATH]; if (!GetConfigPath(szConfigPath)) return false; // Load the file. int iResult = Xml.Load(szConfigPath); if (iResult != XMLRES_OK && iResult != XMLRES_FILEERROR) { TCHAR szMessage[128]; lsnprintf_s(szMessage,128,lngGetString(ERROR_LOADSETTINGS),iResult); MessageBox(HWND_DESKTOP,szMessage,lngGetString(GENERAL_WARNING),MB_OK | MB_ICONWARNING); return false; } if (!Xml.EnterElement(_T("InfraRecorder"))) return false; if (!Xml.EnterElement(_T("Settings"))) return false; for (unsigned int i = 0; i < m_Settings.size(); i++) { if (!m_Settings[i]->Load(&Xml)) bResult = false; } Xml.LeaveElement(); Xml.LeaveElement(); return bResult; } ================================================ FILE: src/app/settings_manager.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "settings.hh" class CSettingsManager { private: std::vector m_Settings; void RegisterObject(ISettings *pSettings); bool GetConfigPath(TCHAR *szConfigPath); public: CSettingsManager(); ~CSettingsManager(); bool Save(); bool Load(); }; extern CSettingsManager g_SettingsManager; ================================================ FILE: src/app/stdafx.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #if (_ATL_VER < 0x0700) #include #endif ================================================ FILE: src/app/stdafx.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #pragma warning (disable: 4100) // "unreferenced formal parameter". #pragma warning (disable: 4706) // "assignment within conditional expression". // Change these values to use different versions. #define WINVER 0x0400 #define _WIN32_WINNT 0x0500 #define _WIN32_IE 0x0500 #define _RICHEDIT_VER 0x0100 #define VERSION_COMPATIBILITY_CHECK #include #include extern CAppModule _Module; #include #include #include #include #include #include // CWaitCursor #include // CSplitterWindowImpl #include #include // WM_DEVICECHANGE. #include "atl_compat.hh" #include using namespace ckcore; // Manifest. #if defined _M_IX86 #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='x86' publicKeyToken='6595b64144ccf1df' language='*'\"") #elif defined _M_IA64 #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='ia64' publicKeyToken='6595b64144ccf1df' language='*'\"") #elif defined _M_X64 #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='amd64' publicKeyToken='6595b64144ccf1df' language='*'\"") #else #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='*' publicKeyToken='6595b64144ccf1df' language='*'\"") #endif // Button image list support. #if (_WIN32_WINNT < 0x501) #define BUTTON_IMAGELIST_ALIGN_CENTER 4 typedef struct { HIMAGELIST himl; // Index: Normal, hot pushed, disabled. If count is less than 4, we use index 1 RECT margin; // Margin around icon. UINT uAlign; } BUTTON_IMAGELIST, *PBUTTON_IMAGELIST; #define BCM_FIRST 0x1600 #define BCM_SETIMAGELIST (BCM_FIRST + 0x0002) #endif ================================================ FILE: src/app/string_table.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "string_table.hh" const TCHAR *g_szStringTable[END_OF_STRING_TABLE_GUARD] = { #define TRSTR(a,b) b, #include "translated_strings.hh" #undef TRSTR }; _STATIC_ASSERT(END_OF_STRING_TABLE_GUARD == _countof(g_szStringTable)); ================================================ FILE: src/app/string_table.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ enum eStringTable { #define TRSTR(a,b) a, #include "translated_strings.hh" #undef TRSTR END_OF_STRING_TABLE_GUARD }; extern const TCHAR *g_szStringTable[END_OF_STRING_TABLE_GUARD]; ================================================ FILE: src/app/temp_manager.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "temp_manager.hh" #include "settings.hh" CTempManager g_TempManager; CTempManager::CTempManager() { m_szEmptyDir[0] = '\0'; } CTempManager::~CTempManager() { } /* CTempManager::AddObject ----------------------- Adds a new file or folder to the list of files and folder to be removed when the application closes. Please note that directories has to be empty to be able to remove them. */ void CTempManager::AddObject(const TCHAR *szFileName) { m_szFileNames.push_back(szFileName); } void CTempManager::CleanUp() { // Remove the empty directory (if created). ckcore::Directory::remove(m_szEmptyDir); m_szEmptyDir[0] = '\0'; // Remove any files. for (unsigned int i = 0; i < m_szFileNames.size(); i++) { ckcore::File File(m_szFileNames[i].c_str()); ckcore::Directory Directory(m_szFileNames[i].c_str()); if (File.exist()) File.remove(); else if (Directory.exist()) Directory.remove(); } m_szFileNames.clear(); } const TCHAR *CTempManager::GetEmtpyDirectory() { if (m_szEmptyDir[0] == '\0') { ckcore::Directory TempDir = ckcore::Directory::temp(); TempDir.create(); lstrcpy(m_szEmptyDir,TempDir.name().c_str()); } return m_szEmptyDir; } ================================================ FILE: src/app/temp_manager.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include class CTempManager { private: std::vector m_szFileNames; // Temporary empty directory. TCHAR m_szEmptyDir[MAX_PATH]; public: CTempManager(); ~CTempManager(); void AddObject(const TCHAR *szFileName); void CleanUp(); const TCHAR *GetEmtpyDirectory(); }; extern CTempManager g_TempManager; ================================================ FILE: src/app/toolbar_manager.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "toolbar_manager.hh" #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" #include "trans_util.hh" #include "main_frm.hh" CToolBarManager g_ToolBarManager; CToolBarManager::CCustomizeDlg::CCustomizeDlg(int iText,int iIcon) { m_iText = iText; m_iIcon = iIcon; } CToolBarManager::CCustomizeDlg::~CCustomizeDlg() { } LRESULT CToolBarManager::CCustomizeDlg::OnInitDialog(UINT uMsg,WPARAM wParam, LPARAM lParam,BOOL &bHandled) { // Increase the window height. RECT rcWindow,rcClient; GetWindowRect(&rcWindow); GetClientRect(&rcClient); rcWindow.bottom += 58; SetWindowPos(0,0,0,rcWindow.right - rcWindow.left,rcWindow.bottom - rcWindow.top,SWP_NOZORDER | SWP_NOMOVE); // Create the text options label. RECT rcTextStatic = { 6,rcClient.bottom + 2,80,rcClient.bottom + 19 }; HWND hWndStatic = m_TextStatic.Create(m_hWnd,rcTextStatic,lngGetString(TBCUSTOMIZE_TEXTOPTIONS), WS_CHILD | WS_VISIBLE | WS_GROUP); m_TextStatic.SetFont(AtlGetDefaultGuiFont()); int iTextRight = UpdateStaticWidth(m_hWnd,hWndStatic,lngGetString(TBCUSTOMIZE_TEXTOPTIONS)); // Create the text options combo box. RECT rcTextCombo = { 80,rcClient.bottom,263,rcClient.bottom + 200 }; m_TextComboBox.Create(m_hWnd,rcTextCombo,NULL,WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | CBS_DROPDOWNLIST | CBS_AUTOHSCROLL, 0,IDC_TBCUSTOMIZE_TEXTCOMBO); m_TextComboBox.SetFont(AtlGetDefaultGuiFont()); m_TextComboBox.AddString(lngGetString(TBCUSTOMIZE_SHOWTEXT)); m_TextComboBox.AddString(lngGetString(TBCUSTOMIZE_SHOWTEXTRIGHT)); m_TextComboBox.AddString(lngGetString(TBCUSTOMIZE_NOTEXT)); m_TextComboBox.SetCurSel(m_iText); // Create the icon options label. RECT rcIconStatic = { 6,rcClient.bottom + 31,80,rcClient.bottom + 48 }; hWndStatic = m_IconStatic.Create(m_hWnd,rcIconStatic,lngGetString(TBCUSTOMIZE_ICONOPTIONS), WS_CHILD | WS_VISIBLE | WS_GROUP); m_IconStatic.SetFont(AtlGetDefaultGuiFont()); int iIconRight = UpdateStaticWidth(m_hWnd,hWndStatic,lngGetString(TBCUSTOMIZE_ICONOPTIONS)); // Create the icon options combo box. RECT rcIconCombo = { 80,rcClient.bottom + 29,263,rcClient.bottom + 200 }; m_IconComboBox.Create(m_hWnd,rcIconCombo,NULL,WS_CHILD | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | CBS_DROPDOWNLIST | CBS_AUTOHSCROLL, 0,IDC_TBCUSTOMIZE_ICONCOMBO); m_IconComboBox.SetFont(AtlGetDefaultGuiFont()); m_IconComboBox.AddString(lngGetString(TBCUSTOMIZE_ICONSMALL)); m_IconComboBox.AddString(lngGetString(TBCUSTOMIZE_ICONLARGE)); m_IconComboBox.SetCurSel(m_iIcon); // Update the static width if necessary. int iMaxRight = iTextRight > iIconRight ? iTextRight : iIconRight; if (iMaxRight > 80) { UpdateEditPos(m_hWnd,IDC_TBCUSTOMIZE_TEXTCOMBO,iMaxRight,true); UpdateEditPos(m_hWnd,IDC_TBCUSTOMIZE_ICONCOMBO,iMaxRight,true); } bHandled = false; return 0; } LRESULT CToolBarManager::CCustomizeDlg::OnTCSelChange(WORD wNotifyCode,WORD wID, HWND hWndCtl,BOOL &bHandled) { m_iText = m_TextComboBox.GetCurSel(); bHandled = false; return 0; } LRESULT CToolBarManager::CCustomizeDlg::OnICSelChange(WORD wNotifyCode,WORD wID, HWND hWndCtl,BOOL &bHandled) { m_iIcon = m_IconComboBox.GetCurSel(); bHandled = false; return 0; } int CToolBarManager::CCustomizeDlg::GetTextOption() { return m_iText; } int CToolBarManager::CCustomizeDlg::GetIconOption() { return m_iIcon; } CToolBarManager::CToolBarManager() { m_pToolBar = NULL; Reset(); } CToolBarManager::~CToolBarManager() { } void CToolBarManager::AddSeparator() { TBBUTTON tbButton; tbButton.fsState = TBSTATE_ENABLED; tbButton.fsStyle = TBSTYLE_SEP; tbButton.iBitmap = NULL; tbButton.idCommand = NULL; tbButton.iString = NULL; tbButton.dwData = NULL; m_Buttons[ID_TOOLBAR_SEPARATOR] = tbButton; } void CToolBarManager::AddButton(int iCommand,int iBitmap,int iString) { TBBUTTON tbButton; tbButton.fsState = TBSTATE_ENABLED; tbButton.fsStyle = TBSTYLE_BUTTON | TBSTYLE_AUTOSIZE; tbButton.iBitmap = iBitmap; tbButton.idCommand = iCommand; tbButton.iString = NULL; tbButton.dwData = iString; m_Buttons[iCommand] = tbButton; } void CToolBarManager::AddDropDownButton(int iBitmap,int iCommand,int iString) { TBBUTTON tbButton; tbButton.fsState = TBSTATE_ENABLED; tbButton.fsStyle = TBSTYLE_BUTTON | BTNS_DROPDOWN | TBSTYLE_AUTOSIZE; tbButton.iBitmap = iBitmap; tbButton.idCommand = iCommand; tbButton.iString = NULL; tbButton.dwData = iString; m_Buttons[iCommand] = tbButton; } void CToolBarManager::Reset() { m_Buttons.clear(); m_SelButtons.clear(); // Add all different buttons to the internal button structure. AddButton(ID_FILE_OPEN,0,TOOLBAR_OPEN); AddButton(ID_FILE_SAVE,1,TOOLBAR_SAVE); AddButton(ID_FILE_PROJECTPROPERTIES,3,TOOLBAR_PROJECTPROPERTIES); AddButton(ID_APP_EXIT,4,TOOLBAR_EXIT); AddButton(ID_BURNCOMPILATION_COMPACTDISC,8,TOOLBAR_BURNCOMPILATION); AddButton(ID_ACTIONS_BURNIMAGE,9,TOOLBAR_BURNIMAGE); AddButton(ID_COPYDISC_COMPACTDISC,10,TOOLBAR_COPY); AddButton(ID_ACTIONS_MANAGETRACKS,11,TOOLBAR_TRACKS); AddButton(ID_ACTIONS_ERASERE,12,TOOLBAR_ERASE); AddButton(ID_ACTIONS_FIXATEDISC,13,TOOLBAR_FIXATE); AddButton(ID_VIEW_PROGRAMLOG,14,TOOLBAR_LOG); AddButton(ID_OPTIONS_CONFIGURATION,15,TOOLBAR_CONFIGURATION); AddButton(ID_OPTIONS_DEVICES,16,TOOLBAR_DEVICES); AddButton(ID_HELP_HELPTOPICS,17,TOOLBAR_HELP); AddButton(ID_APP_ABOUT,18,TOOLBAR_ABOUT); AddSeparator(); // Setup the default toolbar button configuration. m_SelButtons.push_back(ID_FILE_OPEN); m_SelButtons.push_back(ID_FILE_SAVE); m_SelButtons.push_back(ID_TOOLBAR_SEPARATOR); m_SelButtons.push_back(ID_BURNCOMPILATION_COMPACTDISC); m_SelButtons.push_back(ID_ACTIONS_BURNIMAGE); m_SelButtons.push_back(ID_COPYDISC_COMPACTDISC); m_SelButtons.push_back(ID_ACTIONS_ERASERE); m_SelButtons.push_back(ID_TOOLBAR_SEPARATOR); m_SelButtons.push_back(ID_OPTIONS_CONFIGURATION); m_SelButtons.push_back(ID_OPTIONS_DEVICES); m_SelButtons.push_back(ID_TOOLBAR_SEPARATOR); m_SelButtons.push_back(ID_APP_EXIT); } bool CToolBarManager::FillToolBarCtrl(CToolBarCtrl *pToolBar) { m_pToolBar = pToolBar; pToolBar->SetButtonStructSize(); std::vector::const_iterator itButtons; int iIndex = 0; for (itButtons = m_SelButtons.begin(); itButtons != m_SelButtons.end(); itButtons++,iIndex++) { // Should be use button text? if (g_DynamicSettings.m_iToolBarText == TOOLBAR_TEXT_DONTSHOW) m_Buttons[*itButtons].iString = (unsigned int)NULL; else m_Buttons[*itButtons].iString = (INT_PTR)lngGetString((unsigned int)m_Buttons[*itButtons].dwData); if (!pToolBar->InsertButton(iIndex,&m_Buttons[*itButtons])) return false; } return true; } bool CToolBarManager::Save(CXmlProcessor *pXml) { if (pXml == NULL) return false; pXml->AddElement(_T("Buttons"),_T(""),true); TCHAR szTemp[16]; int iIndex = 0; std::vector::const_iterator itSelButton; for (itSelButton = m_SelButtons.begin(); itSelButton != m_SelButtons.end(); itSelButton++,iIndex++) { lsprintf(szTemp,_T("Item%i"),iIndex); pXml->AddElement(szTemp,*itSelButton); } pXml->LeaveElement(); return true; } bool CToolBarManager::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("Buttons"))) return false; m_SelButtons.clear(); TCHAR szTemp[16]; for (unsigned int i = 0; i < pXml->GetElementChildCount(); i++) { lsprintf(szTemp,_T("Item%i"),i); int iButton = -1; pXml->GetSafeElementData(szTemp,&iButton); m_SelButtons.push_back(iButton); } pXml->LeaveElement(); return true; } bool CToolBarManager::Customize() { if (m_pToolBar == NULL) return false; m_pCustomizeDlg = new CCustomizeDlg(g_DynamicSettings.m_iToolBarText, g_DynamicSettings.m_iToolBarIcon); m_hCBTHook = ::SetWindowsHookEx(WH_CBT,CBTProc,0,::GetCurrentThreadId()); m_pToolBar->Customize(); ::UnhookWindowsHookEx(m_hCBTHook); m_hCBTHook = NULL; // Fix to make sure that the toolbar is appropriately updated according the its buttons. if (m_pCustomizeDlg->GetTextOption() == TOOLBAR_TEXT_SHOW && g_DynamicSettings.m_iToolBarText != TOOLBAR_TEXT_SHOW) { SIZE sButton; sButton.cx = 50; sButton.cy = 50; m_pToolBar->SetButtonSize(sButton); } // Update the settings. g_DynamicSettings.m_iToolBarText = m_pCustomizeDlg->GetTextOption(); g_DynamicSettings.m_iToolBarIcon = m_pCustomizeDlg->GetIconOption(); delete m_pCustomizeDlg; m_pCustomizeDlg = NULL; // Update the toolbar style. unsigned long ulStyle = m_pToolBar->GetStyle() & (~TBSTYLE_LIST); ulStyle |= g_DynamicSettings.m_iToolBarText == TOOLBAR_TEXT_SHOWRIGHT ? TBSTYLE_LIST : 0; m_pToolBar->SetStyle(ulStyle); // Update the button selection map. m_SelButtons.clear(); for (int i = 0; i < m_pToolBar->GetButtonCount(); i++) { TBBUTTON tbButton; m_pToolBar->GetButton(i,&tbButton); if (tbButton.fsStyle & TBSTYLE_SEP) m_SelButtons.push_back(ID_TOOLBAR_SEPARATOR); else m_SelButtons.push_back(tbButton.idCommand); } // Delete all buttons. for (int i = m_pToolBar->GetButtonCount() - 1; i >= 0; i--) m_pToolBar->DeleteButton(i); switch (g_DynamicSettings.m_iToolBarIcon) { case TOOLBAR_ICON_SMALL: m_pToolBar->SetImageList(g_pMainFrame->GetToolBarSmall()); break; case TOOLBAR_ICON_LARGE: m_pToolBar->SetImageList(g_pMainFrame->GetToolBarLarge()); break; } // Re-add all buttons. FillToolBarCtrl(m_pToolBar); // Update toolbar height. int iButtonHeight = HIWORD(m_pToolBar->GetButtonSize()); RECT rcToolBar; m_pToolBar->GetWindowRect(&rcToolBar); GetParentWindow(m_pToolBar).ScreenToClient(&rcToolBar); m_pToolBar->MoveWindow(rcToolBar.left,rcToolBar.top,rcToolBar.right - rcToolBar.left,iButtonHeight); // Repaint. m_pToolBar->Invalidate(); return true; } LRESULT CToolBarManager::OnToolBarBeginAdjust(int idCtrl,LPNMHDR pNMH,BOOL &bHandled) { bHandled = false; return 0; } CToolBarManager::CCustomizeDlg *CToolBarManager::m_pCustomizeDlg = NULL; HHOOK CToolBarManager::m_hCBTHook = NULL; LRESULT CALLBACK CToolBarManager::CBTProc(int nCode,WPARAM wParam,LPARAM lParam) { try { if ((nCode == HCBT_CREATEWND) && (m_pCustomizeDlg) && (m_pCustomizeDlg->m_hWnd == NULL)) { // Subclass standard customize toolbar dialog. HWND hWnd = (HWND)wParam; m_pCustomizeDlg->SubclassWindow(hWnd); } } catch (...) // If exception is not caught then we can get in infinite loop as assert window is opened. { // Call next hook. LRESULT lResult = ::CallNextHookEx(m_hCBTHook,nCode,wParam,lParam); ::UnhookWindowsHookEx(m_hCBTHook); m_hCBTHook = NULL; if (m_pCustomizeDlg) { delete m_pCustomizeDlg; m_pCustomizeDlg = NULL; } return lResult; } return ::CallNextHookEx(m_hCBTHook,nCode,wParam,lParam); } LRESULT CToolBarManager::OnToolBarInitCustomize(int idCtrl,LPNMHDR pNMH,BOOL &bHandled) { // Remove the help button. bHandled = true; return TBNRF_HIDEHELP; } LRESULT CToolBarManager::OnToolBarQueryInsert(int idCtrl,LPNMHDR pNMH,BOOL &bHandled) { bHandled = true; return true; } LRESULT CToolBarManager::OnToolBarQueryDelete(int idCtrl,LPNMHDR pNMH,BOOL &bHandled) { bHandled = true; return true; } LRESULT CToolBarManager::OnToolBarGetButtonInfo(int idCtrl,LPNMHDR pNMH,BOOL &bHandled) { LPTBNOTIFY lpTbNotify = (LPTBNOTIFY)pNMH; if (lpTbNotify->iItem < (int)m_Buttons.size()) { std::map::const_iterator itButton = m_Buttons.begin(); for (int i = 0; i < lpTbNotify->iItem; i++) itButton++; lpTbNotify->tbButton = itButton->second; lpTbNotify->tbButton.iString = (INT_PTR)lngGetString( (unsigned int)lpTbNotify->tbButton.dwData); lstrcpy(lpTbNotify->pszText,lngGetString( (unsigned int)lpTbNotify->tbButton.dwData)); lpTbNotify->cchText = lstrlen(lpTbNotify->pszText); // Syncronize with the menu. If the corresponding menu item is disabled // the toolbar button should be disabled as well. /*CMenuItemInfo mii; mii.fMask = MIIM_STATE; if (GetMenuItemInfo(g_pMainFrame->m_CmdBar.GetMenu(),lpTbNotify->tbButton.idCommand,FALSE,&mii)) { if (mii.fState & MFS_DISABLED) lpTbNotify->tbButton.fsState = TBSTATE_INDETERMINATE; else lpTbNotify->tbButton.fsState = TBSTATE_ENABLED; }*/ bHandled = true; return true; } bHandled = false; return 0; } LRESULT CToolBarManager::OnToolBarReset(int idCtrl,LPNMHDR pNMH,BOOL &bHandled) { // Reset the toolbar button configuration. Reset(); // Delete all buttons. for (int i = m_pToolBar->GetButtonCount() - 1; i >= 0; i--) m_pToolBar->DeleteButton(i); // Re-add all buttons. FillToolBarCtrl(m_pToolBar); bHandled = true; return 0; } ================================================ FILE: src/app/toolbar_manager.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include #include "resource.h" class CToolBarManager { private: class CCustomizeDlg : public CWindowImpl { private: CStatic m_TextStatic; CStatic m_IconStatic; CComboBox m_TextComboBox; CComboBox m_IconComboBox; int m_iText; int m_iIcon; public: CCustomizeDlg(int iText,int iIcon); ~CCustomizeDlg(); int GetTextOption(); int GetIconOption(); BEGIN_MSG_MAP(CCustomizeDlg) COMMAND_HANDLER(IDC_TBCUSTOMIZE_TEXTCOMBO,CBN_SELCHANGE,OnTCSelChange) COMMAND_HANDLER(IDC_TBCUSTOMIZE_ICONCOMBO,CBN_SELCHANGE,OnICSelChange) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnTCSelChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnICSelChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; enum { ID_TOOLBAR_SEPARATOR = 0 }; CToolBarCtrl *m_pToolBar; std::map m_Buttons; std::vector m_SelButtons; void AddButton(int iBitmap,int iCommand,int iString); void AddDropDownButton(int iBitmap,int iCommand,int iString); void AddSeparator(); void Reset(); // Customize dialog hook. static CCustomizeDlg *m_pCustomizeDlg; static HHOOK m_hCBTHook; static LRESULT CALLBACK CBTProc(int nCode,WPARAM wParam,LPARAM lParam); public: CToolBarManager(); ~CToolBarManager(); bool FillToolBarCtrl(CToolBarCtrl *pToolBar); bool Save(CXmlProcessor *pXml); bool Load(CXmlProcessor *pXml); bool Customize(); // Events. LRESULT OnToolBarBeginAdjust(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnToolBarInitCustomize(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnToolBarQueryInsert(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnToolBarQueryDelete(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnToolBarGetButtonInfo(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); LRESULT OnToolBarReset(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); }; extern CToolBarManager g_ToolBarManager; ================================================ FILE: src/app/translated_strings.hh ================================================ TRSTR(GENERAL_ERROR /* 0x0000 */, _T("Error")) TRSTR(GENERAL_WARNING /* 0x0001 */, _T("Warning")) TRSTR(GENERAL_INFORMATION /* 0x0002 */, _T("Information")) TRSTR(GENERAL_QUESTION /* 0x0003 */, _T("Question")) TRSTR(ERROR_REGISTRYWRITE /* 0x0004 */, _T("Unable to write to the registry. Your user account might not have permissions to perform the requested operation.")) TRSTR(ERROR_FILEWRITE /* 0x0005 */, _T("An error occured while trying to save the file. The file has not been successfully created.")) TRSTR(ERROR_LOADSETTINGS /* 0x0006 */, _T("Unable to load the configuration file, it may be corrupt. The XML processor returned: %d.")) TRSTR(ERROR_AUDIOADDFOLDER /* 0x0007 */, _T("You can't add folders to an audio project.")) TRSTR(ERROR_LOADPROJECTXML /* 0x0008 */, _T("Unable to parse project file, it may be corrupt. The XML processor returned: %d.")) TRSTR(ERROR_LOADPROJECT /* 0x0009 */, _T("Unable to parse project file, it may be corrupt.")) TRSTR(ERROR_PROJECTVERSION /* 0x000a */, _T("The project has been created with a newer version of InfraRecorder. You need to update InfraRecorder to open this project.")) TRSTR(ERROR_UNSUPCHARSET /* 0x000b */, _T("The active character set could not be automatically detected. The registry suggests the following body character set: %s.")) TRSTR(ERROR_RELOADDRIVE /* 0x000c */, _T("Please reload the drive and press the 'Reload' button.")) TRSTR(ERROR_SECTOR /* 0x000d */, _T("Error on sector %d not corrected.")) TRSTR(ERROR_COMMANDLINE /* 0x000e */, _T("The internal command line is too long for your system to handle. The length limit on your system is %d characters. Please try to shorten the file paths in your project and try again.")) // OBSOLETE. TRSTR(CONFIRM_AUTORUNENABLED /* 0x000f */, _T("InfraRecorder has noticed that autorun is enabled. Leaving autorun enabled causes Windows to poll the CD drive while recording, which might damage your CD. Do you want to turn off autorun (recommended)?")) TRSTR(CONFIRM_WRITECANCEL /* 0x0010 */, _T("Are you sure that you want to abort the operation? Aborting might damage your CD permanently.")) TRSTR(CONFIRM_REMOVEITEMS /* 0x0011 */, _T("Are you sure that you want to remove the selected item(s) from the project?")) TRSTR(CONFIRM_SAVEPROJECT /* 0x0012 */, _T("The project has been modified, do you want to save the changes?")) TRSTR(CONFIRM_CREATEMIXIMAGE /* 0x0013 */, _T("Only the data track can be recorded to a disc image from mixed-mode projects. Do you want to continue?")) TRSTR(INIT_SCANBUS /* 0x0014 */, _T("Scanning SCSI/IDE bus...")) TRSTR(INIT_LOADCAPABILITIES /* 0x0015 */, _T("Loading device capabilities...")) TRSTR(STRINGTABLE_PLACEHOLDER0 /* 0x0016 */, _T("")) TRSTR(INIT_FOUNDDEVICES /* 0x0017 */, _T("InfraRecorder has detected changes in your hardware configuration. Would you like to update your device configuration now?")) TRSTR(INIT_DEVICECD /* 0x0018 */, _T("Initializing device...")) TRSTR(INIT_TRACK /* 0x0019 */, _T("Loading information from track %d.")) TRSTR(FAILURE_SCANBUS /* 0x001a */, _T("InfraRecorder failed to scan your SCSI/IDE busses. Please make sure that your system is properly configured.")) TRSTR(FAILURE_LOADCAP /* 0x001b */, _T("InfraRecorder failed to load device capabilities.")) TRSTR(FAILURE_LOADINFOEX /* 0x001c */, _T("InfraRecorder failed to load extended device information.")) TRSTR(FAILURE_NORECORDERS /* 0x001d */, _T("No recorders available")) TRSTR(FAILURE_NODEVICES /* 0x001e */, _T("No devices available")) TRSTR(FAILURE_CDRTOOLS /* 0x001f */, _T("An error occured while trying to perform the selected operation.")) TRSTR(FAILURE_NOMEDIA /* 0x0020 */, _T("Unable to load drive media. Please insert a valid disc into the drive.")) TRSTR(FAILURE_UNSUPRW /* 0x0021 */,_T("The disc is not rewritable or your recorder might not support the operation.")) TRSTR(FAILURE_ERASE /* 0x0022 */, _T("Couldn't erase disc using the selected method.")) TRSTR(FAILURE_BADSECTORSIZE /* 0x0023 */, _T("Unsupported sector size of %d bytes.")) TRSTR(FAILURE_WRITE /* 0x0024 */, _T("A write error occurred. Please see program log for more details.")) TRSTR(FAILURE_UNSUPAUDIO /* 0x0025 */, _T("The file you are trying to add is not supported.")) TRSTR(FAILURE_FILENOTFOUND /* 0x0026 */, _T("Unable to locate the file:")) TRSTR(FAILURE_CREATECDTEXT /* 0x0027 */, _T("An error occured while trying to save the CD-Text binary data. The CD-Text information will not be recorded.")) TRSTR(FAILURE_AUDIOCODING /* 0x0028 */, _T("Inappropriate audio coding in file:")) TRSTR(FAILURE_LOADDRIVE /* 0x0029 */, _T("The drive could not automatically be reloaded.")) TRSTR(FAILURE_READSOURCEDISC /* 0x002a */, _T("Can't read source disc. Retrying from sector %d.")) TRSTR(FAILURE_DEEPDIR /* 0x002b */, _T("The directory structure is too deep for '%s' (%d), maximum allowed depth is %d.")) TRSTR(FAILURE_DVDSUPPORT /* 0x002c */, _T("DVD media found. DVD write support is not available in this version.")) // Project properties. TRSTR(PROJECTPROP_TITLE /* 0x002d */, _T("Project Properties")) TRSTR(PROJECTPROP_ISOLEVEL1 /* 0x002e */, _T("Level 1 (11 character file names)")) TRSTR(PROJECTPROP_ISOLEVEL2 /* 0x002f */, _T("Level 2 (31 character file names)")) TRSTR(PROJECTPROP_ISOLEVEL3 /* 0x0030 */, _T("Level 3 (files larger than 4 GiB)")) TRSTR(PROJECTPROP_MODE1 /* 0x0031 */, _T("Mode 1")) TRSTR(PROJECTPROP_MODE2 /* 0x0032 */, _T("Mode 2 XA (multisession)")) TRSTR(PROJECTPROP_TRACKPROP /* 0x0033 */, _T("Properties of Track %d")) // Container titles. TRSTR(TITLE_EXPLORERVIEW /* 0x0034 */, _T("Explorer View")) TRSTR(TITLE_PROJECTVIEW /* 0x0035 */, _T("Disc Layout")) // Miscellaneous. TRSTR(MISC_MAXIMUM /* 0x0036 */, _T("Maximum")) TRSTR(MISC_NOTAVAILABLE /* 0x0037 */, _T("Not available")) TRSTR(MISC_BURN /* 0x0038 */, _T("Burn ")) TRSTR(MISC_BURNCOMPILATION /* 0x0039 */, _T("Burn Compilation")) TRSTR(MISC_NEWFOLDER /* 0x003a */, _T("New Folder")) TRSTR(MISC_MINUTES /* 0x003b */, _T("%I64d minutes")) TRSTR(MISC_AUTODETECT /* 0x003c */, _T(" (automatically detected)")) TRSTR(MISC_SPECIFYTRACKFOLDER /* 0x003d */, _T("Please select the folder where you want the track(s) to be saved:")) TRSTR(MISC_SPECIFYFOLDER /* 0x003e */, _T("Please select a folder:")) // Projects. TRSTR(PROJECT_DATA /* 0x003f */, _T("Data Project")) TRSTR(PROJECT_AUDIO /* 0x0040 */, _T("Audio Project")) TRSTR(PROJECT_MIXED /* 0x0041 */, _T("Mixed-Mode CD Project")) TRSTR(PROJECT_CONTENTS /* 0x0042 */, _T("%I64d Files, %I64d Folders, %I64d Tracks")) // Properties. TRSTR(PROPERTIES_TITLE /* 0x0043 */, _T("Properties of ")) TRSTR(PROPERTIES_DEVICELOC /* 0x0044 */, _T("Bus %d, Target %d, Lun %d")) // Advanced properties. TRSTR(ADVPROP_MODE2FORM1 /* 0x0045 */, _T("Read mode 2 form 1 blocks")) TRSTR(ADVPROP_MODE2FORM2 /* 0x0046 */, _T("Read mode 2 form 2 blocks")) TRSTR(ADVPROP_READDIGAUDIO /* 0x0047 */, _T("Read digital audio blocks")) TRSTR(ADVPROP_READMULTSESSION /* 0x0048 */, _T("Read multi-session discs")) TRSTR(ADVPROP_READFIXPACKET /* 0x0049 */, _T("Read fixed-packet CD media using method 2")) TRSTR(ADVPROP_READBARCODE /* 0x004a */, _T("Read CD bar code")) TRSTR(ADVPROP_READRWSUBCODE /* 0x004b */, _T("Read R-W subcode information")) TRSTR(ADVPROP_READRAWPWSC /* 0x004c */, _T("Read raw P-W subcode data from lead in")) TRSTR(ADVPROP_SIMULATION /* 0x004d */, _T("Support test writing (simulation)")) TRSTR(ADVPROP_BUFRECORDING /* 0x004e */, _T("Support Buffer Underrun Free recording")) TRSTR(ADVPROP_C2EP /* 0x004f */, _T("Support C2 error pointers")) TRSTR(ADVPROP_EJECTCDSS /* 0x0050 */, _T("Support CD ejection via START/STOP command")) TRSTR(ADVPROP_CHANGEDISCSIDE /* 0x0051 */, _T("Support changing side of disc")) TRSTR(ADVPROP_INDIVIDUALDP /* 0x0052 */, _T("Support Individual Disc Present feature")) TRSTR(ADVPROP_RETURNCDCN /* 0x0053 */, _T("Return CD media catalog number")) TRSTR(ADVPROP_RETURNCDISRC /* 0x0054 */, _T("Return CD ISRC information")) TRSTR(ADVPROP_DELIVCOMPOSITE /* 0x0055 */, _T("Deliver composite A/V data")) TRSTR(ADVPROP_PLAYAUDIOCD /* 0x0056 */, _T("Play audio discs")) TRSTR(ADVPROP_HASLESIC /* 0x0057 */, _T("Have load-empty-slot-in-changer feature")) TRSTR(ADVPROP_LMOPU /* 0x0058 */, _T("Lock media on power up via prevent jumper")) TRSTR(ADVPROP_ALLOWML /* 0x0059 */, _T("Allow media to be locked in the drive via PREVENT/ALLOW command")) TRSTR(ADVPROP_RESTARTNSDARA /* 0x005a */, _T("Restart non-streamed digital audio reads accurateley")) TRSTR(ADVPROP_RETURNRWSUBCODE /* 0x005b */, _T("Return R-W subcode de-interleaved and error-corrected")) TRSTR(ADVPROP_INDIVIDUALVC /* 0x005c */, _T("Support individual channel volume settings")) TRSTR(ADVPROP_INDEPENDENTMUTE /* 0x005d */, _T("Support independent mute setting for each channel")) TRSTR(ADVPROP_DOPORT1 /* 0x005e */, _T("Support digital output on port 1")) TRSTR(ADVPROP_DOPORT2 /* 0x005f */, _T("Support digital output on port 2")) TRSTR(ADVPROP_DOSENDDIGDAT /* 0x0060 */, _T("Send digital data LSB-first")) TRSTR(ADVPROP_DOSETLRCK /* 0x0061 */, _T("Set LRCK high for left-channel data")) TRSTR(ADVPROP_HASVALIDDATA /* 0x0062 */, _T("Have valid data on falling edge of clock")) TRSTR(DEVICETYPE_CDREADER /* 0x0063 */, _T("CD-Reader")) TRSTR(DEVICETYPE_DVDREADER /* 0x0064 */, _T("CD/DVD-Reader")) TRSTR(DEVICETYPE_CDRECORDER /* 0x0065 */, _T("CD-Recorder")) TRSTR(DEVICETYPE_DVDRECORDER /* 0x0066 */, _T("CD/DVD-Recorder")) // Disc blanking. TRSTR(BLANKMODE_FULL /* 0x0067 */, _T("Blank the entire disc")) TRSTR(BLANKMODE_MINIMAL /* 0x0068 */, _T("Minimally blank the disc")) TRSTR(BLANKMODE_UNCLOSE /* 0x0069 */, _T("Unclose last session")) TRSTR(BLANKMODE_SESSION /* 0x006a */, _T("Blank last session")) // Write methods. TRSTR(WRITEMODE_SAO /* 0x006b */, _T("Session-At-Once (SAO)")) TRSTR(WRITEMODE_TAO /* 0x006c */, _T("Track-At-Once (TAO)")) TRSTR(WRITEMODE_TAONOPREGAP /* 0x006d */, _T("TAO with zero pregap")) TRSTR(WRITEMODE_RAW96R /* 0x006e */, _T("Raw writing (raw96r)")) TRSTR(WRITEMODE_RAW16 /* 0x006f */, _T("Raw writing (raw16)")) TRSTR(WRITEMODE_RAW96P /* 0x0070 */, _T("Raw writing (raw96p)")) // Eject menu. TRSTR(EJECTMENU_NODRIVES /* 0x0071 */, _T("(no drives found)")) // Write modes. TRSTR(WRITEMODE_REAL /* 0x0072 */, _T("real write")) TRSTR(WRITEMODE_SIMULATION /* 0x0073 */, _T("simulation")) // Column titles. TRSTR(COLUMN_TIME /* 0x0074 */, _T("Time")) TRSTR(COLUMN_EVENT /* 0x0075 */, _T("Event")) TRSTR(COLUMN_ID /* 0x0076 */, _T("ID")) TRSTR(COLUMN_VENDOR /* 0x0077 */, _T("Vendor")) TRSTR(COLUMN_IDENTIFICATION /* 0x0078 */, _T("Identification")) TRSTR(COLUMN_REVISION /* 0x0079 */, _T("Revision")) TRSTR(COLUMN_NAME /* 0x007a */, _T("Name")) TRSTR(COLUMN_SIZE /* 0x007b */, _T("Size")) TRSTR(COLUMN_TYPE /* 0x007c */, _T("Type")) TRSTR(COLUMN_MODIFIED /* 0x007d */, _T("Modified")) TRSTR(COLUMN_PATH /* 0x007e */, _T("Path")) TRSTR(COLUMN_TRACK /* 0x007f */, _T("Track")) TRSTR(COLUMN_TITLE /* 0x0080 */, _T("Title")) TRSTR(COLUMN_LENGTH /* 0x0081 */, _T("Length")) TRSTR(COLUMN_LOCATION /* 0x0082 */, _T("Location")) TRSTR(COLUMN_ARTIST /* 0x0083 */, _T("Artist")) TRSTR(COLUMN_ADDRESS /* 0x0084 */, _T("Address")) TRSTR(COLUMN_DESCRIPTION /* 0x0085 */, _T("Description")) TRSTR(COLUMN_EXTENSIONS /* 0x0086 */, _T("Extensions")) // Status dialog. TRSTR(PROGRESS_STATUS /* 0x0087 */, _T("Status: ")) TRSTR(PROGRESS_DEVICE /* 0x0088 */, _T("Device: ")) TRSTR(PROGRESS_TOTAL /* 0x0089 */, _T("Total progress: %d%%")) TRSTR(PROGRESS_INIT /* 0x008a */, _T("Preparing to perform the selected operation.")) TRSTR(PROGRESS_DONE /* 0x008b */, _T("Operation completed.")) TRSTR(PROGRESS_CANCELED /* 0x008c */, _T("Operation canceled.")) TRSTR(PROGRESS_GRACETIME /* 0x008d */, _T("Last chance to abort, operation will start in %d seconds.")) TRSTR(PROGRESS_BEGINERASE /* 0x008e */, _T("Started to erase disc in %s mode.")) TRSTR(PROGRESS_BEGINFIXATE /* 0x008f */, _T("Started to close disc in %s mode.")) TRSTR(PROGRESS_BEGINWRITE /* 0x0090 */, _T("Started to write disc in %s mode.")) TRSTR(PROGRESS_BEGINTRACK /* 0x0091 */, _T("Started to write track %d.")) TRSTR(PROGRESS_BEGINDISCIMAGE /* 0x0092 */, _T("Started to write disc image.")) TRSTR(PROGRESS_IMAGEDEVICE /* 0x0093 */, _T("Virtual Disc Image Recorder")) TRSTR(PROGRESS_BEGINREADTRACK /* 0x0094 */, _T("Started to read track %d.")) TRSTR(PROGRESS_BEGINSCANTRACK /* 0x0095 */, _T("Started to scan track %d.")) TRSTR(PROGRESS_BEGINREADDISC /* 0x0096 */, _T("Started to read disc.")) // Status strings. TRSTR(STATUS_ERASE /* 0x0097 */, _T("Erasing disc.")) TRSTR(STATUS_WRITEDATA /* 0x0098 */, _T("Writing data.")) // FIXME: Obsolete. TRSTR(STATUS_WRITE /* 0x0099 */, _T("Writing track %d of %d at %.1fx speed.")) // FIXME: Obsolete. TRSTR(STATUS_WRITEPREGAP /* 0x009a */, _T("Writing pregap for track %d at %ld.")) // FIXME: Obsolete. TRSTR(STATUS_FILLBUFFER /* 0x009b */, _T("Waiting for reader process to fill input buffer.")) // FIXME: Obsolete. TRSTR(STATUS_FIXATE /* 0x009c */, _T("Closing disc.")) // FIXME: Obsolete. TRSTR(STATUS_WRITEIMAGE /* 0x009d */, _T("Writing disc image.")) TRSTR(STATUS_READTRACK /* 0x009e */, _T("Reading track.")) TRSTR(STATUS_SCANTRACK /* 0x009f */, _T("Scanning track.")) TRSTR(STATUS_C2TOTAL /* 0x00a0 */, _T("Found %d bytes of C2 errors in %d sectors.")) TRSTR(STATUS_C2RATE /* 0x00a1 */, _T("The C2 error rate is %f%%.")) TRSTR(STATUS_READDISC /* 0x00a2 */, _T("Reading disc.")) // FIXME: Obsolete. // Status titles. TRSTR(STITLE_ERASE /* 0x00a3 */, _T("Erasing Disc")) TRSTR(STITLE_BURNIMAGE /* 0x00a4 */, _T("Burning Image")) TRSTR(STITLE_CREATEIMAGE /* 0x00a5 */, _T("Creating Image")) TRSTR(STITLE_BURNCOMPILATION /* 0x00a6 */,_T("Burning Compilation")) TRSTR(STITLE_FIXATE /* 0x00a7 */, _T("Closing Disc")) TRSTR(STITLE_READTRACK /* 0x00a8 */, _T("Reading Track")) TRSTR(STITLE_SCANTRACK /* 0x00a9 */, _T("Scanning Track")) TRSTR(STITLE_COPYDISC /* 0x00aa */, _T("Copying Disc")) // Sucess messages. TRSTR(SUCCESS_ERASE /* 0x00ab */, _T("The disc was successfully erased.")) TRSTR(SUCCESS_WRITE /* 0x00ac */, _T("The data was successfully written to the disc."))// FIXME: Obsolete. TRSTR(SUCCESS_FIXATE /* 0x00ad */, _T("The disc was successfully closed.")) // FIXME: Obsolete. TRSTR(SUCCESS_CREATEIMAGE /* 0x00ae */, _T("The disc image was successfully created.")) TRSTR(SUCCESS_READTRACK /* 0x00af */, _T("Done reading track %d.")) TRSTR(SUCCESS_SCANTRACK /* 0x00b0 */, _T("Done scanning track %d.")) TRSTR(SUCCESS_READDISC /* 0x00b1 */, _T("Done reading disc.")) // FIXME: Obsolete. // Warning messages. TRSTR(WARNING_FIXATE /* 0x00b2 */, _T("Some drives don't like closing in simulation mode.")) // FIXME: Obsolete. // Information messages. TRSTR(INFO_UNSUPERASEMODE /* 0x00b3 */, _T("Some recorders does not support all erase modes.")) // FIXME: Obsolete. TRSTR(INFO_ERASERETRY /* 0x00b4 */, _T("You can try the erase entire disc method.")) // FIXME: Obsolete. // Property page titles. TRSTR(TITLE_GENERAL /* 0x00b5 */, _T("General")) TRSTR(TITLE_ADVANCED /* 0x00b6 */, _T("Advanced")) TRSTR(TITLE_FIELDS /* 0x00b7 */, _T("Fields")) TRSTR(TITLE_AUDIO /* 0x00b8 */, _T("Audio")) TRSTR(TITLE_CONFIGURATION /* 0x00b9 */, _T("Configuration")) TRSTR(TITLE_LANGUAGE /* 0x00ba */, _T("Language")) TRSTR(TITLE_SHELLEXT /* 0x00bb */, _T("Shell Extension")) // Copy disc. TRSTR(COPYDISC_TITLE /* 0x00bc */, _T("Copy Disc")) // Disc information. TRSTR(DISC_UNKNOWN /* 0x00bd */, _T("Unknown")) TRSTR(DISC_SEQUENTIAL /* 0x00be */, _T("(sequential)")) TRSTR(DISC_RESTRICTEDOVERWRITE /* 0x00bf */, _T("(restricted overwrite)")) TRSTR(DISC_REVISION /* 0x00c0 */, _T("revision")) TRSTR(DISC_NOREGION /* 0x00c1 */, _T("Not region protected")) TRSTR(DISC_BLANK /* 0x00c2 */, _T("blank")) TRSTR(DISC_INCOMPLETE /* 0x00c3 */, _T("incomplete")) TRSTR(DISC_FIXATED /* 0x00c4 */, _T("closed")) TRSTR(DISC_RANDOMACCESS /* 0x00c5 */, _T("random access")) TRSTR(DISC_EMPTY /* 0x00c6 */, _T("empty")) TRSTR(DISC_RESERVED /* 0x00c7 */, _T("reserved")) TRSTR(DISC_COMPLETE /* 0x00c8 */, _T("complete")) TRSTR(DISC_NOT /* 0x00c9 */, _T("not ")) TRSTR(DISC_STATUS /* 0x00ca */, _T("The disc is %s, the last session is %s, the disc can %sbe erased.")) // Miscellaneous. TRSTR(WARNING_DISCSIZE /* 0x00cb */, _T("The data may not fit on the current disc."))// FIXME: Obsolete. TRSTR(FAILURE_OPENSESSION /* 0x00cc */, _T("Could not open a new session.")) // FIXME: Obsolete. // Added version 0.40. TRSTR(ERROR_LOADCODECS /* 0x00cd */, _T("An error occured while trying to load the installed codecs. Please make sure that the installed codecs are compatible with this version of InfraRecorder.")) TRSTR(PROGRESS_DECODETRACKS /* 0x00ce */, _T("Decoding audio tracks.")) TRSTR(ERROR_NODECODER /* 0x00cf */, _T("Unable to find a suitable decoder for the audio file: %s.")) TRSTR(ERROR_WAVECODEC /* 0x00d0 */, _T("Unable to find the wave encoder. Please verify your codec configuration.")) TRSTR(ERROR_CODECINIT /* 0x00d1 */, _T("Failed to initialize the %s encoder (%d,%d,%d,%I64d).")) TRSTR(ERROR_ENCODEDATA /* 0x00d2 */, _T("Encoder failed, could not encode data.")) TRSTR(SUCCESS_DECODETRACK /* 0x00d3 */, _T("Decoded the audio file: %s.")) TRSTR(ERROR_TARGETFOLDER /* 0x00d4 */, _T("The selected target folder is invalid. Please select another target folder.")) TRSTR(SUCCESS_ENCODETRACK /* 0x00d5 */, _T("Encoded the audio file: %s.")) TRSTR(PROGRESS_ENCODETRACK /* 0x00d6 */, _T("Encoding track (%s).")) // Added version 0.41. TRSTR(ERROR_FIFOSIZE /* 0x00d7 */, _T("Invalid FIFO buffer size. The size must be at least %i MiB and at most %i MiB.")) TRSTR(PROJECTPROP_ISOLEVEL4 /* 0x00d8 */, _T("Level 4 (ISO-9660 version 2)")) TRSTR(WARNING_CLONEWRITEMETHOD /* 0x00d9 */, _T("It's recommended to write a cloned disc using the raw96r or raw16 write method. The selected recorder supports none of these modes.")) TRSTR(TITLE_READ /* 0x00da */, _T("Read")) TRSTR(MISC_AUTO /* 0x00db */, _T("Automatic")) TRSTR(COPYIMAGE_TITLE /* 0x00dc */, _T("Copy to Disc Image")) TRSTR(INFO_COPYDISC /* 0x00dd */, _T("Audio discs and multi-session discs must be copied in clone mode to be copied correctly. Please note that it's not possible to clone a disc on the fly.")) TRSTR(INFO_RAWIMAGE /* 0x00de */, _T("The selected disc image seems to include a TOC-file. It's recommended that you record images that includes a TOC and sub-channel data using a raw write method. InfraRecorder will automatically suggest one for you.")) TRSTR(PROGRESS_BEGINESTIMAGESIZE /* 0x00df */, _T("Started to estimate file system size.")) TRSTR(SUCCESS_ESTIMAGESIZE /* 0x00e0 */, _T("Done estimating file system size (%I64d sectors).")) TRSTR(ERROR_ESTIMAGESIZE /* 0x00e1 */, _T("An error occured while estimating the file system size. Can not continue.")) TRSTR(PROGRESS_ESTIMAGESIZE /* 0x00e2 */, _T("Estimating file system size.")) TRSTR(SPACEMETER_USED /* 0x00e3 */, _T("Used: ")) TRSTR(SPACEMETER_FREE /* 0x00e4 */, _T("Free: ")) TRSTR(ADVPROP_SAO /* 0x00e5 */, _T("Write in session-at-once (SAO) mode")) TRSTR(ADVPROP_TAO /* 0x00e6 */, _T("Write in track-at-once (TAO) mode")) TRSTR(ADVPROP_RAW96R /* 0x00e7 */, _T("Write in raw96r mode")) TRSTR(ADVPROP_RAW16 /* 0x00e8 */, _T("Write in raw16 mode")) TRSTR(ADVPROP_RAW96P /* 0x00e9 */, _T("Write in raw96p mode")) TRSTR(INFO_WRITESPEED /* 0x00ea */, _T("This option should only be changed when InfraRecorder has detected the wrong write speeds. It does not allow your recorder to write faster than its specification or faster than the media allows.")) TRSTR(TITLE_BOOT /* 0x00eb */, _T("Boot")) TRSTR(ERROR_NUMBOOTIMAGES /* 0x00ec */, _T("You can't add more boot images. The maximum number of allowed boot images in one project is 63.")) TRSTR(BOOTEMU_NONE /* 0x00ed */, _T("None")) TRSTR(BOOTEMU_FLOPPY /* 0x00ee */, _T("Floppy")) TRSTR(BOOTEMU_HARDDISK /* 0x00ef */, _T("Hard disk")) TRSTR(COLUMN_EMULATION /* 0x00f0 */, _T("Emulation")) TRSTR(TITLE_EDITBOOTIMAGE /* 0x00f1 */, _T("Edit Boot Image")) // Added version 0.42. TRSTR(PROJECT_DVDVIDEO /* 0x00f2 */, _T("DVD-Video Project")) TRSTR(WARNING_OLDPROJECT /* 0x00f3 */, _T("The project you are trying to open is created by an older version of InfraRecorder. It might not open correctly.")) TRSTR(MISC_SPECIFYDVDFOLDER /* 0x00f4 */, _T("Please select the folder that contains all the DVD-files that you want to record. The folder should include a subfolder named VIDEO_TS:")) TRSTR(ERROR_INVALIDDVDFOLDER /* 0x00f5 */, _T("The selected folder does not contain a valid DVD-Video file structure (the folder VIDEO_TS is missing). Please select another folder.")) TRSTR(FAILURE_WRITELEADIN /* 0x00f6 */, _T("A write error occurred. Failed to write lead-in.")) // FIXME: Obsolete. TRSTR(FAILURE_INITDRIVE /* 0x00f7 */, _T("Failed to initialize the recorder.")) // FIXME: Obsolete. TRSTR(FAILURE_DVDRWDUMMY /* 0x00f8 */, _T("DVD+RW discs can not be written in simulation mode."))// FIXME: Obsolete. TRSTR(PROGRESS_RELOADMEDIA /* 0x00f9 */, _T("Reloading media.")) TRSTR(STATUS_VERIFY /* 0x00fa */, _T("Verifying '%s'.")) TRSTR(SUCCESS_VERIFY /* 0x00fb */, _T("Done verifying disc. No errors found.")) TRSTR(FAILURE_VERIFY /* 0x00fc */, _T("Done verifying disc, %d read error(s) occured.")) TRSTR(PROGRESS_BEGINVERIFY /* 0x00fd */, _T("Started disc verification.")) TRSTR(FAILURE_VERIFYNOFILE /* 0x00fe */, _T("The file '%s' could not be found on the disc.")) TRSTR(FAILURE_VERIFYREADERROR /* 0x00ff */, _T("Read error in '%s' (0x%.8X != 0x%.8X).")) TRSTR(STRINGTABLE_PLACEHOLDER1 = 0x0100, _T("")) TRSTR(STRINGTABLE_PLACEHOLDER2 = 0x0101, _T("")) TRSTR(STRINGTABLE_PLACEHOLDER3 = 0x0102, _T("")) // Added version 0.43. TRSTR(DRIVELETTER_TITLE /* 0x0103 */, _T("Drive Letter of %s %s %s")) TRSTR(FORMATMODE_QUICK /* 0x0104 */, _T("Quick format")) TRSTR(FORMATMODE_FULL /* 0x0105 */, _T("Full format")) TRSTR(MEDIA_INSERT /* 0x0106 */, _T("(please insert a disc)")) TRSTR(MEDIA_UNSUPPORTED /* 0x0107 */, _T("(unsupported media)")) TRSTR(STATUS_FORMAT /* 0x0108 */, _T("Formatting disc.")) TRSTR(STATUS_FORMATBKGND /* 0x0109 */, _T("Formatting disc in background.")) TRSTR(STATUS_CLOSETRACK /* 0x010a */, _T("Closing track.")) TRSTR(PROGRESS_BEGINFORMAT /* 0x010b */, _T("Started to format disc in %s mode.")) TRSTR(FAILURE_FORMAT /* 0x010c */, _T("Could not format the disc.")) TRSTR(FAILURE_STOPBKGNDFORMAT /* 0x010d */, _T("Could not stop the background format process.")) TRSTR(SUCCESS_FORMAT /* 0x010e */, _T("The disc was successfully formatted.")) // Added version 0.44. TRSTR(STATUS_REREADSECTOR /* 0x010f */, _T("Reading sector %u (retry %u of %u).")) TRSTR(STATUS_READTRACK2 /* 0x0110 */, _T("Reading disc at %.1fx speed.")) TRSTR(ERROR_MOVESAMESRCDST /* 0x0111 */, _T("The destination folder is a subfolder of the source folder.")) TRSTR(MISC_MODIFIED /* 0x0112 */, _T("modified:")) TRSTR(ERROR_EXISTINGFILENAME /* 0x0113 */, _T("The destination folder already contains a file or folder named '%s'.")) TRSTR(TBCUSTOMIZE_TEXTOPTIONS /* 0x0114 */, _T("Text options:")) TRSTR(TBCUSTOMIZE_ICONOPTIONS /* 0x0115 */, _T("Icon options:")) TRSTR(TBCUSTOMIZE_SHOWTEXT /* 0x0116 */, _T("Show text labels")) TRSTR(TBCUSTOMIZE_SHOWTEXTRIGHT /* 0x0117 */, _T("Selective text on right")) TRSTR(TBCUSTOMIZE_NOTEXT /* 0x0118 */, _T("No text labels")) TRSTR(TBCUSTOMIZE_ICONSMALL /* 0x0119 */, _T("Small icons")) TRSTR(TBCUSTOMIZE_ICONLARGE /* 0x011a */, _T("Large icons")) TRSTR(TOOLBAR_OPEN /* 0x011b */, _T("Open")) TRSTR(TOOLBAR_SAVE /* 0x011c */, _T("Save")) TRSTR(TOOLBAR_PROJECTPROPERTIES /* 0x011d */, _T("Properties")) TRSTR(TOOLBAR_EXIT /* 0x011e */, _T("Exit")) TRSTR(TOOLBAR_BURNCOMPILATION /* 0x011f */, _T("Burn Project")) TRSTR(TOOLBAR_BURNIMAGE /* 0x0120 */, _T("Burn Image")) TRSTR(TOOLBAR_COPY /* 0x0121 */, _T("Copy")) TRSTR(TOOLBAR_TRACKS /* 0x0122 */, _T("Tracks")) TRSTR(TOOLBAR_ERASE /* 0x0123 */, _T("Erase")) TRSTR(TOOLBAR_FIXATE /* 0x0124 */, _T("Close")) TRSTR(TOOLBAR_LOG /* 0x0125 */, _T("Log")) TRSTR(TOOLBAR_CONFIGURATION /* 0x0126 */, _T("Configuration")) TRSTR(TOOLBAR_DEVICES /* 0x0127 */, _T("Devices")) TRSTR(TOOLBAR_HELP /* 0x0128 */, _T("Help")) TRSTR(TOOLBAR_ABOUT /* 0x0129 */, _T("About")) TRSTR(STRINGTABLE_PLACEHOLDER4 /* 0x012a */, _T("")) TRSTR(MEDIA_INSERTBLANK /* 0x012b */, _T("(please insert a blank disc)")) TRSTR(INFO_INSERTBLANK /* 0x012c */, _T("Please insert the blank disc which should be recorded.")) TRSTR(INFO_INSERTSOURCE /* 0x012d */, _T("Please insert the source disc that should be copied.")) TRSTR(WARNING_NOFIXATION /* 0x012e */, _T("Please note that disabling the closing step does not create a multi-session disc. Please see the help documentation for more information.")) // Added version 0.45. TRSTR(INFO_RELOAD /* 0x012f */, _T("Unable to automatically reload the media. Please try to reload it manually, and then press OK.")) TRSTR(PROGRESS_FAILED /* 0x0130 */, _T("Operation failed.")) TRSTR(FAILURE_CREATEIMAGE /* 0x0131 */, _T("Failed to create disc image.")) TRSTR(TITLE_FILESYSTEM /* 0x0132 */, _T("File System")) TRSTR(ERROR_IMPORTSESSION /* 0x0133 */, _T("Unable to import session, could not list disc contents.")) TRSTR(MISC_SESSION /* 0x0134 */, _T("Session")) TRSTR(MISC_TRACK /* 0x0135 */, _T("track")) TRSTR(MISC_MODE /* 0x0136 */, _T("mode")) TRSTR(MISC_ERASENONEMPTY /* 0x0137 */, _T("The inserted disc does not appear to be empty, do you want to erase it first?")) TRSTR(WARNING_IMPORTFS /* 0x0138 */, _T("Multi-session discs require an ISO9660 file system (without any additional file systems). Do you want InfraRecorder to change your project to use this file system and continue?")) TRSTR(STITLE_VERIFYDISC /* 0x0139 */, _T("Verifying Disc")) // Added version 0.46. TRSTR(ERROR_NUMCOPIES /* 0x013a */, _T("Invalid number of copies. Please specify a number larger than zero.")) TRSTR(INFO_NEXTCOPY /* 0x013b */, _T("Please insert a new blank disc to create another copy.")) TRSTR(INFO_CREATECOPY /* 0x013c */, _T("Creating copy %d of %d.")) // Added version 0.50. TRSTR(ERROR_PROJECT_IMPORT /* 0x013d */, _T("Unable to import, does the selected source file exist?")) TRSTR(ERROR_PROJECT_IMPORT_FILE /* 0x013e */, _T("Could not import the file \"%s\".")) TRSTR(COLUMN_DRIVE /* 0x013f */, _T("Drive")) TRSTR(CONFIRM_CREATE_DIR_PATH /* 0x0140 */, _T("Directory \"%s\" does not exist. Do you want it to be created?" )) TRSTR(CANNOT_CREATE_DIR_PATH /* 0x0141 */, _T("Cannot create directory \"%s\"." )) TRSTR(WARNING_MISSPROJFILE /* 0x0142 */, _T("The project file \"%s\" could not be found on your computer. It will be removed from the project.")) TRSTR(WARNING_NODEVICES /* 0x0143 */, _T("InfraRecorder was unable to find any disc devices in your system.\n\nPlease note that Windows 2000, XP and 2003 systems require administrator permissions to access disc devices. Often this can be circumvented by changing your system settings. Please consult the InfraRecorder FAQ in the manual for further information.")) // Added version 0.53. TRSTR(STITLE_PREPOPERATION /* 0x0144 */, _T("Preparing Operation")) TRSTR(STATUS_GATHER_FILE_INFO /* 0x0145 */, _T("Gathering project file information.")) TRSTR(PROJECTPROP_ISO_CHARSET_ISO /* 0x0146 */, _T("ISO9660 (standard)")) TRSTR(WARNING_BAD_DVDVIDEO /* 0x00147 */, _T("InfraRecorder video projects requires the content to be in DVD-Video format. This does not appear to be the case. InfraRecorder could not find the required file: VIDEO_TS/VIDEO_TS.IFO.\n\nPlease convert any video files into DVD-Video format before burning them as video projects in InfraRecorder.\n\nDo you want to continue anyways?")) TRSTR(WARNING_EMPTY_PROJECT /* 0x00148 */, _T("You have no added any files to the current project. Do you want to continue, creating an empty file system?")) ================================================ FILE: src/app/tree_manager.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "main_frm.hh" #include "string_table.hh" #include "temp_manager.hh" #include "settings.hh" #include "project_manager.hh" #include "lang_util.hh" #include "audio_util.hh" #include "infrarecorder.hh" #include "tree_manager.hh" CTreeManager g_TreeManager; /* CItemData */ CItemData::CItemData() { m_szFileName[0] = '\0'; m_szFilePath[0] = '\0'; m_pAudioData = NULL; m_pIsoData = NULL; szFullPath[0] = '\0'; szFileType[0] = '\0'; usFileDate = 0; usFileTime = 0; uiSize = 0; /*uiTrackLength = 0; szTrackTitle[0] = '\0'; szTrackArtist[0] = '\0';*/ ucFlags = 0; } CItemData::~CItemData() { // Free any optional data. if (m_pAudioData != NULL) { delete m_pAudioData; m_pAudioData = NULL; } if (m_pIsoData != NULL) { delete m_pIsoData; m_pIsoData = NULL; } } void CItemData::FileNameChanged() { /*if (ucFlags & PROJECTITEM_FLAG_ISBOOTIMAGE) { CProjectBootImage *pBootImage = g_ProjectSettings.GetBootImage(szFullPath); if (pBootImage != NULL) { pBootImage->m_LocalName = m_szFileName; } }*/ } void CItemData::FilePathChanged() { /*if (ucFlags & PROJECTITEM_FLAG_ISBOOTIMAGE) { CProjectBootImage *pBootImage = g_ProjectSettings.GetBootImage(szFullPath); if (pBootImage != NULL) { pBootImage->m_LocalPath = m_szFilePath; } }*/ } void CItemData::SetFileName(const TCHAR *szFileName) { lstrcpy(m_szFileName,szFileName); FileNameChanged(); } const TCHAR *CItemData::GetFileName() { return m_szFileName; } void CItemData::SetFilePath(const TCHAR *szFilePath) { lstrcpy(m_szFilePath,szFilePath); FilePathChanged(); } const TCHAR *CItemData::GetFilePath() { return m_szFilePath; } TCHAR *CItemData::BeginEditFileName() { return m_szFileName; } void CItemData::EndEditFileName() { FileNameChanged(); } TCHAR *CItemData::BeginEditFilePath() { return m_szFilePath; } void CItemData::EndEditFilePath() { FilePathChanged(); } CItemData::CAudioData *CItemData::GetAudioData() { if (m_pAudioData == NULL) m_pAudioData = new CAudioData(); return m_pAudioData; } bool CItemData::HasAudioData() { return m_pAudioData != NULL; } CItemData::CIsoData *CItemData::GetIsoData() { if (m_pIsoData == NULL) m_pIsoData = new CIsoData(); return m_pIsoData; } bool CItemData::HasIsoData() { return m_pIsoData != NULL; } /* CProjectNode */ void CProjectNode::Sort(unsigned int uiSortColumn,bool bSortUp,bool bSortAudio) { CChildComparator ChildComparator(uiSortColumn,bSortUp,bSortAudio); CFileComparator FileComparator(uiSortColumn,bSortUp,bSortAudio); m_Children.sort(ChildComparator); m_Files.sort(FileComparator); } /* CChildComparator */ bool CChildComparator::operator() (const CProjectNode *pSafeNode1, const CProjectNode *pSafeNode2) { CItemData *pItemData1,*pItemData2; if (m_bSortUp) { pItemData1 = pSafeNode1->pItemData; pItemData2 = pSafeNode2->pItemData; } else { pItemData1 = pSafeNode2->pItemData; pItemData2 = pSafeNode1->pItemData; } switch (m_uiSortColumn) { case COLUMN_SUBINDEX_NAME: return lstrcmp(pItemData1->GetFileName(),pItemData2->GetFileName()) < 0; // No reason to sort these columns, they are all the same. case COLUMN_SUBINDEX_TYPE: case COLUMN_SUBINDEX_SIZE: return false; case COLUMN_SUBINDEX_MODIFIED: FILETIME ftFileTime1,ftFileTime2; DosDateTimeToFileTime(pItemData1->usFileDate,pItemData1->usFileTime,&ftFileTime1); DosDateTimeToFileTime(pItemData2->usFileDate,pItemData2->usFileTime,&ftFileTime2); return CompareFileTime(&ftFileTime1,&ftFileTime2) < 0; case COLUMN_SUBINDEX_PATH: return lstrcmp(pItemData1->GetFilePath(),pItemData2->GetFilePath()) < 0; } return true; } /* CFileComparator */ bool CFileComparator::operator() (const CItemData *pSafeItemData1, const CItemData *pSafeItemData2) { CItemData *pItemData1,*pItemData2; if (m_bSortUp) { pItemData1 = (CItemData *)pSafeItemData1; pItemData2 = (CItemData *)pSafeItemData2; } else { pItemData1 = (CItemData *)pSafeItemData2; pItemData2 = (CItemData *)pSafeItemData1; } if (!m_bSortAudio) { switch (m_uiSortColumn) { case COLUMN_SUBINDEX_NAME: return lstrcmp(pItemData1->GetFileName(),pItemData2->GetFileName()) < 0; case COLUMN_SUBINDEX_TYPE: return lstrcmp(pItemData1->szFileType,pItemData2->szFileType) < 0; case COLUMN_SUBINDEX_MODIFIED: FILETIME ftFileTime1,ftFileTime2; DosDateTimeToFileTime(pItemData1->usFileDate,pItemData1->usFileTime,&ftFileTime1); DosDateTimeToFileTime(pItemData2->usFileDate,pItemData2->usFileTime,&ftFileTime2); return CompareFileTime(&ftFileTime1,&ftFileTime2) < 0; case COLUMN_SUBINDEX_SIZE: if (pItemData1->uiSize < pItemData2->uiSize) return true; else return false; case COLUMN_SUBINDEX_PATH: return lstrcmp(pItemData1->GetFilePath(),pItemData2->GetFilePath()) < 0; } } else { switch (m_uiSortColumn) { case COLUMN_SUBINDEX_TRACK: return true; case COLUMN_SUBINDEX_TITLE: { // If no title is specified the file name is displayed. const TCHAR *szTitle1 = pItemData1->GetAudioData()->szTrackTitle; if (szTitle1[0] == '\0') szTitle1 = pItemData1->GetFileName(); const TCHAR *szTitle2 = pItemData2->GetAudioData()->szTrackTitle; if (szTitle2[0] == '\0') szTitle2 = pItemData2->GetFileName(); return lstrcmp(szTitle1,szTitle2) < 0; } case COLUMN_SUBINDEX_LENGTH: if (pItemData1->GetAudioData()->uiTrackLength < pItemData2->GetAudioData()->uiTrackLength) return true; else return false; case COLUMN_SUBINDEX_LOCATION: return lstrcmp(pItemData1->szFullPath,pItemData2->szFullPath) < 0; } } return true; } /* CTreeManager */ CTreeManager::CTreeManager() { m_pTreeView = NULL; m_pListView = NULL; } CTreeManager::~CTreeManager() { // Destroy the tree if it hasn't been destroyed. DestroyTree(); } void CTreeManager::AssignControls(CTreeViewCtrlEx *pTreeView,CListViewCtrl *pListView) { m_pTreeView = pTreeView; m_pListView = pListView; } HTREEITEM CTreeManager::AddTreeNode(HTREEITEM hParentItem,CProjectNode *pNode) { TV_ITEM tvItem = { 0 }; TV_INSERTSTRUCT tvInsert = { 0 }; tvItem.mask = TVIF_PARAM | TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_CHILDREN; tvItem.pszText = LPSTR_TEXTCALLBACK; tvItem.iImage = PROJECTTREE_IMAGEINDEX_FOLDER; tvItem.lParam = (LPARAM)pNode; tvItem.cChildren = false; tvInsert.item = tvItem; tvInsert.hInsertAfter = TVI_LAST; tvInsert.hParent = hParentItem; HasChildren(hParentItem,true); // Insert the tree item. pNode->m_hTreeItem = m_pTreeView->InsertItem(&tvInsert); return pNode->m_hTreeItem; } HTREEITEM CTreeManager::GetTreeChildFromParent(HTREEITEM hParentItem,TCHAR *szText) { HTREEITEM hItem = m_pTreeView->GetChildItem(hParentItem); while (hItem) { CProjectNode *pNode = (CProjectNode *)m_pTreeView->GetItemData(hItem); if (pNode) { if (!lstrcmp(pNode->pItemData->GetFileName(),szText)) return hItem; } hItem = m_pTreeView->GetNextVisibleItem(hItem); } return NULL; } bool CTreeManager::HasChildren(HTREEITEM hItem,bool bHasChildren) { TVITEM tvItem = { 0 }; tvItem.hItem = hItem; tvItem.mask = TVIF_CHILDREN; m_pTreeView->GetItem(&tvItem); tvItem.cChildren = bHasChildren; if (SUCCEEDED(m_pTreeView->SetItem(&tvItem))) return true; return false; } CProjectNode *CTreeManager::GetDirFromParent(CProjectNode *pParent,const TCHAR *szName) { std::list ::iterator itNodeObject; for (itNodeObject = pParent->m_Children.begin(); itNodeObject != pParent->m_Children.end(); itNodeObject++) { CProjectNode *pChild = *itNodeObject; if (!lstrcmp(pChild->pItemData->GetFileName(),szName)) return pChild; } return m_pRootNode; } /* CTreeManager::GetNodeFromPath ----------------------------- Returns the CProjectNode that corresponds to the specified path. */ CProjectNode *CTreeManager::GetNodeFromPath(const TCHAR *szPath) { int iLastDelimiter = 0; CProjectNode *pCurrentNode = m_pRootNode; for (int i = 0; i < lstrlen(szPath); i++) { if (szPath[i] == '\\' || szPath[i] == '/') { TCHAR *szSubPath = SubString(szPath,iLastDelimiter,i - iLastDelimiter); pCurrentNode = GetDirFromParent(pCurrentNode,szSubPath); delete [] szSubPath; iLastDelimiter = i + 1; } } // UPDATE: 2007-02-01 //return pCurrentNode; return pCurrentNode == m_pRootNode ? NULL : pCurrentNode; } CProjectNode *CTreeManager::AddPath(const TCHAR *szPath) { CProjectNode *pFoundNode = GetNodeFromPath(szPath); if (pFoundNode != NULL) return pFoundNode; return NodalizePath(szPath); } /* FIXME: The following function is very similar to GetDirFromParent. */ CProjectNode *CTreeManager::GetChildFromParent(CProjectNode *pParentNode,const TCHAR *szText) { std::list ::iterator itNodeObject; for (itNodeObject = pParentNode->m_Children.begin(); itNodeObject != pParentNode->m_Children.end(); itNodeObject++) { CProjectNode *pChildNode = *itNodeObject; if (pChildNode) { if (!lstrcmp(pChildNode->pItemData->GetFileName(),szText)) return pChildNode; } } return NULL; } CProjectNode *CTreeManager::NodalizePath(const TCHAR *szPath) { CProjectNode *pParentNode = m_pRootNode; HTREEITEM hParentTreeNode = m_pRootNode->m_hTreeItem; int iLastDelimiter = 1; int iPathLength = lstrlen(szPath); // The first character should always be '\\' or '/'. for (int i = 1; i < iPathLength; i++) { if (szPath[i] == '\\' || szPath[i] == '/') { TCHAR *szText = SubString(szPath,iLastDelimiter,i - iLastDelimiter); CProjectNode *pTemp = GetChildFromParent(pParentNode,szText); // Local tree item. HTREEITEM hTreeTemp = NULL; if (m_pTreeView != NULL) hTreeTemp = GetTreeChildFromParent(hParentTreeNode,szText); // Create the new node. if (pTemp == NULL) { CProjectNode *pChildNode = new CProjectNode(pParentNode); // Item text. pChildNode->pItemData->SetFileName(szText); // Get the system icon index. SHFILEINFO shFileInfo; // HACK: Force a folder icon to be used. if (SHGetFileInfo(_T(""),FILE_ATTRIBUTE_DIRECTORY,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_SYSICONINDEX | SHGFI_TYPENAME)) { pChildNode->iIconIndex = shFileInfo.iIcon; lstrcpy(pChildNode->pItemData->szFileType,shFileInfo.szTypeName); } TCHAR *szFilePath = pChildNode->pItemData->BeginEditFilePath(); lstrcpy(szFilePath,pParentNode->pItemData->GetFilePath()); lstrcat(szFilePath,pParentNode->pItemData->GetFileName()); lstrcat(szFilePath,_T("/")); pChildNode->pItemData->EndEditFilePath(); pParentNode->m_Children.push_back(pChildNode); pParentNode = pChildNode; // Local tree item. if (m_pTreeView != NULL) hParentTreeNode = AddTreeNode(hParentTreeNode,pChildNode); } else { pParentNode = pTemp; // Local tree item. hParentTreeNode = hTreeTemp; } iLastDelimiter = i + 1; delete [] szText; } } return pParentNode; } void CTreeManager::ListNode(CProjectNode *pNode) { unsigned int uiItemCount = 0; std::list ::iterator itNodeObject; for (itNodeObject = pNode->m_Children.begin(); itNodeObject != pNode->m_Children.end(); itNodeObject++) { // Add the item to the listview. LVITEM lvi = { 0 }; lvi.mask = LVIF_TEXT | LVIF_IMAGE | LVIF_PARAM; lvi.iItem = uiItemCount++; lvi.iSubItem = 0; lvi.pszText = LPSTR_TEXTCALLBACK; lvi.cchTextMax = MAX_PATH - 1; lvi.iImage = I_IMAGECALLBACK; lvi.lParam = (LPARAM)((CProjectNode *)*itNodeObject)->pItemData; m_pListView->InsertItem(&lvi); } std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) { // Add the item to the listview. LVITEM lvi = { 0 }; lvi.mask = LVIF_TEXT | LVIF_IMAGE | LVIF_PARAM; lvi.iItem = uiItemCount++; lvi.iSubItem = 0; lvi.pszText = LPSTR_TEXTCALLBACK; lvi.cchTextMax = MAX_PATH - 1; lvi.iImage = I_IMAGECALLBACK; lvi.lParam = (LPARAM)*itFileObject; m_pListView->InsertItem(&lvi); } } void CTreeManager::SelectPath(const TCHAR *szPath) { int iLastDelimiter = 0; CProjectNode *pCurrentNode = m_pRootNode; m_pListView->DeleteAllItems(); for (int i = 0; i < lstrlen(szPath); i++) { if (szPath[i] == '\\' || szPath[i] == '/') { TCHAR *szTempPath = SubString(szPath,iLastDelimiter,i - iLastDelimiter); pCurrentNode = GetDirFromParent(pCurrentNode,szTempPath); delete [] szTempPath; iLastDelimiter = i + 1; } } ListNode(pCurrentNode); // Copy the path to m_szCurrentPath. if (pCurrentNode == m_pRootNode) lstrcpy(m_szCurrentPath,_T("/")); else lstrcpy(m_szCurrentPath,szPath); m_pCurrentNode = pCurrentNode; // FIXME: Sort the list view. /*tSortData SortData; SortData.iSubItem = g_MainFrame->m_ListViewHeader.m_iSortCol; SortData.bSortUp = g_MainFrame->m_ListViewHeader.m_bSortUp; g_MainFrame->m_ListView.SortItemsEx(g_MainFrame->MainListViewCompareProc,(LPARAM)&SortData);*/ } void CTreeManager::Refresh() { m_pListView->DeleteAllItems(); ListNode(m_pCurrentNode); m_pTreeView->Expand(m_pRootNode->m_hTreeItem); } void CTreeManager::CreateTree(const TCHAR *szRootName,int iImage) { // We need to make sure that any previous tree is destroyed. DestroyTree(); // Allocate memory for a new root node. m_pRootNode = new CProjectNode(NULL); m_pRootNode->iIconIndex = iImage; m_pRootNode->pItemData->ucFlags |= PROJECTITEM_FLAG_ISPROJECTROOT; if (m_pTreeView != NULL) { TV_ITEM tvRootNode = { 0 }; TV_INSERTSTRUCT tvInsert = { 0 }; // Set the tree view item parameters. tvRootNode.mask = TVIF_PARAM | TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_CHILDREN; tvRootNode.lParam = (LPARAM)m_pRootNode; tvRootNode.pszText = (TCHAR *)szRootName; tvRootNode.iImage = tvRootNode.iSelectedImage = iImage; tvRootNode.cChildren = false; tvInsert.item = tvRootNode; tvInsert.hInsertAfter = TVI_LAST; // Insert the item to the tree, select it and then expand it. m_pRootNode->m_hTreeItem = m_pTreeView->InsertItem(&tvInsert); // Finally we select the root node. m_pTreeView->SelectItem(m_pRootNode->m_hTreeItem); } // Initialize the paths. m_szCurrentPath[0] = '/'; m_szCurrentPath[1] = '\0'; m_pCurrentNode = m_pRootNode; } CProjectNode *CTreeManager::InsertVirtualRoot(const TCHAR *szNodeName,int iImage) { // Allocate memory for a new node. CProjectNode *pNode = new CProjectNode(m_pRootNode); pNode->iIconIndex = iImage; pNode->pItemData->SetFileName(szNodeName); pNode->pItemData->SetFilePath(_T("/")); pNode->pItemData->ucFlags |= PROJECTITEM_FLAG_ISPROJECTROOT; m_pRootNode->m_Children.push_back(pNode); if (m_pTreeView != NULL) { TV_ITEM tvNode = { 0 }; TV_INSERTSTRUCT tvInsert = { 0 }; // Set the tree view item parameters. tvNode.mask = TVIF_PARAM | TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_CHILDREN; tvNode.lParam = (LPARAM)pNode; tvNode.pszText = (TCHAR *)szNodeName; tvNode.iImage = tvNode.iSelectedImage = iImage; tvNode.cChildren = false; tvInsert.item = tvNode; tvInsert.hInsertAfter = TVI_LAST; tvInsert.hParent = m_pRootNode->m_hTreeItem; // Insert the item to the tree, select it and then expand it. pNode->m_hTreeItem = m_pTreeView->InsertItem(&tvInsert); HasChildren(m_pRootNode->m_hTreeItem,true); m_pTreeView->Expand(m_pRootNode->m_hTreeItem); } return pNode; } void CTreeManager::DestroyTree() { // If the root node hasn't yet been free we free it. if (m_pRootNode) { delete m_pRootNode; m_pRootNode = NULL; } } void CTreeManager::RebuildLocalPaths(CProjectNode *pNode,std::vector &FolderStack) { TCHAR szPath[MAX_PATH]; lstrcpy(szPath,pNode->pItemData->GetFilePath()); lstrcat(szPath,pNode->pItemData->GetFileName()); lstrcat(szPath,_T("/")); std::list ::iterator itNodeObject; for (itNodeObject = pNode->m_Children.begin(); itNodeObject != pNode->m_Children.end(); itNodeObject++) { (*itNodeObject)->pItemData->SetFilePath(szPath); FolderStack.push_back(*itNodeObject); } std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) (*itFileObject)->SetFilePath(szPath); } void CTreeManager::RebuildPaths(const TCHAR *szStartPath) { CProjectNode *pCurNode = GetNodeFromPath(szStartPath); std::vector FolderStack; RebuildLocalPaths(pCurNode,FolderStack); while (FolderStack.size() > 0) { pCurNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); RebuildLocalPaths(pCurNode,FolderStack); } } bool CTreeManager::RemoveEntry(CProjectNode *pNode) { HTREEITEM hParentItem = m_pTreeView->GetParentItem(pNode->m_hTreeItem); if (!hParentItem) return false; // If the item we're deleting is the current directory we need to update // the current directory to the parent. if (pNode == m_pCurrentNode) m_pTreeView->SelectItem(hParentItem); // Remove the node from the path list. TCHAR szFullName[MAX_PATH]; lstrcpy(szFullName,pNode->pItemData->GetFilePath()); lstrcat(szFullName,pNode->pItemData->GetFileName()); // Delete the node. m_pTreeView->DeleteItem(pNode->m_hTreeItem); CProjectNode *pParent = (CProjectNode *)m_pTreeView->GetItemData(hParentItem); pParent->m_Children.remove(pNode); delete pNode; if (pParent->m_Children.size() == 0) HasChildren(pParent->m_hTreeItem,false); return true; } /* CTreeManager::RemoveEntry ------------------------- Removes the child or file entry in pNode that points to the same data as the pItemData pointer. It returns true if the item was found, otherwise false. All data associated with the pItemData object will be deallocated. */ bool CTreeManager::RemoveEntry(CProjectNode *pNode,CItemData *pItemData) { // Look for matching nodes. CProjectNode *pFoundNode = NULL; std::list ::iterator itNodeObject; for (itNodeObject = pNode->m_Children.begin(); itNodeObject != pNode->m_Children.end(); itNodeObject++) { if ((*itNodeObject)->pItemData == pItemData) { pFoundNode = *itNodeObject; break; } } // It's not safe to remove the node from the iterating loop so we need // to remove it here. if (pFoundNode != NULL) { // Delete the node. m_pTreeView->DeleteItem(pFoundNode->m_hTreeItem); delete pFoundNode; pNode->m_Children.remove(pFoundNode); if (pNode->m_Children.size() == 0) HasChildren(pNode->m_hTreeItem,false); return true; } // If we have reached this far we know that the pItemData belongs to a file. delete pItemData; pNode->m_Files.remove(pItemData); return true; } bool CTreeManager::RemoveEntry(const TCHAR *szLocalPath,const TCHAR *szFullPath) { CProjectNode *pNode = GetNodeFromPath(szLocalPath); std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) { if (!ComparePaths((*itFileObject)->szFullPath,szFullPath)) return RemoveEntry(pNode,(*itFileObject)); } return false; } /* CTreeManager::MoveEntry ----------------------- Moves the item with the specified pItemData in the specified parent to the new parent. The function returns true if successfull, false otherwise (the only valid cause of a failure is when the destination folder is a subfolder of the source folder). */ bool CTreeManager::MoveEntry(CProjectNode *pParent,CItemData *pItemData,CProjectNode *pNewParent) { // Check if we are about to move a file or folder. if (pItemData->ucFlags & PROJECTITEM_FLAG_ISFOLDER) { // Locate the tree node accosiacted with the folder item. CProjectNode *pItemNode = ResolveNode(pParent,pItemData); // The node was not found. if (pItemNode == NULL) return false; // Make sure that the destination folder is not a subfolder of the source folder. if (IsSubNode(pItemNode,pNewParent)) return false; pParent->m_Children.remove(pItemNode); pNewParent->m_Children.push_back(pItemNode); class CParentChild { public: HTREEITEM m_hParent; HTREEITEM m_hChild; CParentChild(HTREEITEM hParent,HTREEITEM hChild) { m_hParent = hParent; m_hChild = hChild; } }; // We need to remember the old node so we can delete it when we're done. HTREEITEM hOldNode = pItemNode->m_hTreeItem; std::queue NodeQueue; NodeQueue.push(CParentChild(pNewParent->m_hTreeItem,pItemNode->m_hTreeItem)); while (!NodeQueue.empty()) { // Insert the current item at the new position. TVITEM tvItem = { 0 }; tvItem.hItem = NodeQueue.front().m_hChild; tvItem.mask = TVIF_PARAM | TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_CHILDREN; m_pTreeView->GetItem(&tvItem); TVINSERTSTRUCT tvInsert = { 0 }; tvInsert.item = tvItem; tvInsert.hInsertAfter = TVI_LAST; tvInsert.hParent = NodeQueue.front().m_hParent; HTREEITEM hNewItem = m_pTreeView->InsertItem(&tvInsert); CProjectNode *pNewNode = (CProjectNode *)m_pTreeView->GetItemData(hNewItem); pNewNode->m_hTreeItem = hNewItem; // Update all file paths. TCHAR *szNewNodePath = pNewNode->pItemData->BeginEditFilePath(); CProjectNode *pParentNode = (CProjectNode *)m_pTreeView->GetItemData(NodeQueue.front().m_hParent); lstrcpy(szNewNodePath,pParentNode->pItemData->GetFilePath()); //IncludeTrailingBackslash(szFilePath); lstrcat(szNewNodePath,pParentNode->pItemData->GetFileName()); lstrcat(szNewNodePath,_T("/")); // Set the same file path for all files in the folder. std::list::iterator itFile; for (itFile = pNewNode->m_Files.begin(); itFile != pNewNode->m_Files.end(); itFile++) { TCHAR *szFilePath = (*itFile)->BeginEditFilePath(); lstrcpy(szFilePath,szNewNodePath); lstrcat(szFilePath,pNewNode->pItemData->GetFileName()); lstrcat(szFilePath,_T("/")); (*itFile)->EndEditFilePath(); } pNewNode->pItemData->EndEditFilePath(); // Add the childs to the queue. HTREEITEM hChild = m_pTreeView->GetChildItem(NodeQueue.front().m_hChild); if (hChild != NULL) { NodeQueue.push(CParentChild(hNewItem,hChild)); while ((hChild = m_pTreeView->GetNextSiblingItem(hChild)) != NULL) NodeQueue.push(CParentChild(hNewItem,hChild)); } NodeQueue.pop(); } // Delete the old node. m_pTreeView->DeleteItem(hOldNode); // Update the old parent's child status if it no longer has any children. if (m_pTreeView->GetChildItem(pParent->m_hTreeItem) == NULL) HasChildren(pParent->m_hTreeItem,false); // Make sure that the new parent knows that it has children. HasChildren(pNewParent->m_hTreeItem,true); } else { pParent->m_Files.remove(pItemData); pNewParent->m_Files.push_back(pItemData); } return true; } /* CTreeManager::IsSubNode ----------------------- Returns true if pNode2 is a sub node of pNode1. */ bool CTreeManager::IsSubNode(CProjectNode *pNode1,CProjectNode *pNode2) { CProjectNode *pCurNode = pNode2; while (pCurNode != NULL) { if (pCurNode == pNode1) return true; pCurNode = pCurNode->m_pParent; } return false; } /* CTreeManager::GetChildItem -------------------------- Checks if pParent has a child node or contains a file with the specified name szName. The function returns the CItemData object of that item. If no such item exists the function returns NULL. */ CItemData *CTreeManager::GetChildItem(CProjectNode *pParent,const TCHAR *szName) { // Check all children of pParent. std::list ::iterator itNodeObject; for (itNodeObject = pParent->m_Children.begin(); itNodeObject != pParent->m_Children.end(); itNodeObject++) { if (!lstrcmp((*itNodeObject)->pItemData->GetFileName(),szName)) return (*itNodeObject)->pItemData; } // Check all files in pParent. std::list ::iterator itFileObject; for (itFileObject = pParent->m_Files.begin(); itFileObject != pParent->m_Files.end(); itFileObject++) { if (!lstrcmp((*itFileObject)->GetFileName(),szName)) return *itFileObject; } return NULL; } /* CTreeManager::GetChildItem -------------------------- Checks if pParent has a child node with the specified name szName. The function returns the CProjectNode object of that child. If no such node exists the function returns NULL. */ CProjectNode *CTreeManager::GetChildNode(CProjectNode *pParent,const TCHAR *szName) { // Check all children of pParent. std::list ::iterator itNodeObject; for (itNodeObject = pParent->m_Children.begin(); itNodeObject != pParent->m_Children.end(); itNodeObject++) { if (!lstrcmp((*itNodeObject)->pItemData->GetFileName(),szName)) return *itNodeObject; } return NULL; } /* CTreeManager::ResolveNode ------------------------- Resolved the CItemData object in the pParent node to the actual node object. The function returns NULL if unsuccessfull. */ CProjectNode *CTreeManager::ResolveNode(CProjectNode *pParent,CItemData *pNodeItem) { std::list ::iterator itNodeObject; for (itNodeObject = pParent->m_Children.begin(); itNodeObject != pParent->m_Children.end(); itNodeObject++) { if ((*itNodeObject)->pItemData == pNodeItem) return *itNodeObject; } return NULL; } void CTreeManager::GetCurrentPath(TCHAR *szCurrentPath) { lstrcpy(szCurrentPath,m_szCurrentPath); } void CTreeManager::SetCurrentPath(const TCHAR *szCurrentPath) { lstrcpy(m_szCurrentPath,szCurrentPath); } CProjectNode *CTreeManager::GetCurrentNode() { return m_pCurrentNode; } CProjectNode *CTreeManager::GetRootNode() { return m_pRootNode; } /* CTreeManager::GetDirFromParent ------------------------------ Returns the CProjectNode object of the sub directory with the name szText which is located inside pParent. */ CProjectNode *CTreeManager::GetDirFromParent(CProjectNode *pParent,TCHAR *szText) { std::list ::iterator itNodeObject; for (itNodeObject = pParent->m_Children.begin(); itNodeObject != pParent->m_Children.end(); itNodeObject++) { CProjectNode *pChild = (CProjectNode *)*itNodeObject; if (!lstrcmp(pChild->pItemData->GetFileName(),szText)) return pChild; } return m_pRootNode; } /* CTreeManager::GetLocalSizeFromNode ---------------------------------- Calculates the size of all the files (not recursivly) in the specified node. */ unsigned __int64 CTreeManager::GetLocalSizeFromNode(CProjectNode *pNode,std::vector &FolderStack) { unsigned __int64 uiSize = 0; std::list ::iterator itNodeObject; for (itNodeObject = pNode->m_Children.begin(); itNodeObject != pNode->m_Children.end(); itNodeObject++) FolderStack.push_back(*itNodeObject); std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) uiSize += (*itFileObject)->uiSize; return uiSize; } /* CTreeManager::GetNodeSize ------------------------- Calculates the size of the specified node. */ unsigned __int64 CTreeManager::GetNodeSize(CProjectNode *pNode) { std::vector FolderStack; unsigned __int64 uiSize = GetLocalSizeFromNode(pNode,FolderStack); while (FolderStack.size() > 0) { pNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); uiSize += GetLocalSizeFromNode(pNode,FolderStack); } return uiSize; } /* CTreeManager::GetNodeSize ------------------------- Calculates the size of the node matching the pItemData pointer in the pParentNode. */ unsigned __int64 CTreeManager::GetNodeSize(CProjectNode *pParentNode,CItemData *pItemData) { CProjectNode *pCurNode = NULL; // Look for matching nodes. std::list ::iterator itNodeObject; for (itNodeObject = pParentNode->m_Children.begin(); itNodeObject != pParentNode->m_Children.end(); itNodeObject++) { if ((*itNodeObject)->pItemData == pItemData) { pCurNode = *itNodeObject; break; } } if (pCurNode == NULL) return 0; return GetNodeSize(pCurNode); // Calulate the size. /*std::vector FolderStack; unsigned __int64 uiSize = GetLocalSizeFromNode(pCurNode,FolderStack); while (FolderStack.size() > 0) { pCurNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); uiSize += GetLocalSizeFromNode(pCurNode,FolderStack); } return uiSize;*/ } void CTreeManager::GetLocalNodeContents(CProjectNode *pNode,std::vector &FolderStack, unsigned __int64 &uiFileCount,unsigned __int64 &uiNodeCount) { std::list ::iterator itNodeObject; for (itNodeObject = pNode->m_Children.begin(); itNodeObject != pNode->m_Children.end(); itNodeObject++) FolderStack.push_back(*itNodeObject); uiFileCount += pNode->m_Files.size(); uiNodeCount += pNode->m_Children.size(); } void CTreeManager::GetNodeContents(CProjectNode *pRootNode,unsigned __int64 &uiFileCount,unsigned __int64 &uiNodeCount) { CProjectNode *pCurNode = pRootNode; uiFileCount = 0; uiNodeCount = 0; // Save the information. std::vector FolderStack; GetLocalNodeContents(pCurNode,FolderStack,uiFileCount,uiNodeCount); while (FolderStack.size() > 0) { pCurNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); GetLocalNodeContents(pCurNode,FolderStack,uiFileCount,uiNodeCount); } } /* CTreeManager::RecursiveLocalSetFlags ------------------------------------ Recursivly sets the specified flags to all files and folder of the specified node. */ void CTreeManager::RecursiveLocalSetFlags(CProjectNode *pNode,std::vector &FolderStack, unsigned char ucFlags) { std::list ::iterator itNodeObject; for (itNodeObject = pNode->m_Children.begin(); itNodeObject != pNode->m_Children.end(); itNodeObject++) { FolderStack.push_back(*itNodeObject); (*itNodeObject)->pItemData->ucFlags |= ucFlags; } std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) (*itFileObject)->ucFlags |= ucFlags; } void CTreeManager::RecursiveSetFlags(CProjectNode *pRootNode,unsigned char ucFlags) { CProjectNode *pCurNode = pRootNode; // Save the information. std::vector FolderStack; RecursiveLocalSetFlags(pCurNode,FolderStack,ucFlags); while (FolderStack.size() > 0) { pCurNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); RecursiveLocalSetFlags(pCurNode,FolderStack,ucFlags); } } void CTreeManager::DeleteImportedItems(CProjectNode *pRootNode) { // Select the root. m_pTreeView->SelectItem(pRootNode->m_hTreeItem); // Find the locked nodes. std::vector FolderStack; std::list ::iterator itNodeObject; for (itNodeObject = pRootNode->m_Children.begin(); itNodeObject != pRootNode->m_Children.end(); itNodeObject++) { if ((*itNodeObject)->pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) FolderStack.push_back(*itNodeObject); } // Remove the locked nodes. TCHAR szFullName[MAX_PATH]; while (FolderStack.size() > 0) { CProjectNode *pCurNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); // Remove the node from the path list. lstrcpy(szFullName,pCurNode->pItemData->GetFilePath()); lstrcat(szFullName,pCurNode->pItemData->GetFileName()); // Delete the node. m_pTreeView->DeleteItem(pCurNode->m_hTreeItem); delete pCurNode; pRootNode->m_Children.remove(pCurNode); } if (pRootNode->m_Children.size() == 0) HasChildren(pRootNode->m_hTreeItem,false); // Find the locked files. std::vector FileStack; std::list ::iterator itFileObject; for (itFileObject = pRootNode->m_Files.begin(); itFileObject != pRootNode->m_Files.end(); itFileObject++) { if ((*itFileObject)->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) FileStack.push_back(*itFileObject); } // Remove the locked files. while (FileStack.size() > 0) { CItemData *pCurFile = FileStack[FileStack.size() - 1]; FileStack.pop_back(); // Delete the file. delete pCurFile; pRootNode->m_Files.remove(pCurFile); } } void CTreeManager::GetNodeFullPaths(CProjectNode *pRootNode,std::vector &FullPaths) { std::list ::iterator itFileObject; for (itFileObject = pRootNode->m_Files.begin(); itFileObject != pRootNode->m_Files.end(); itFileObject++) FullPaths.push_back(((CItemData *)*itFileObject)->szFullPath); } void CTreeManager::GetNodeFiles(CProjectNode *pNode,std::vector &Files) { std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) Files.push_back(*itFileObject); } void CTreeManager::ListNodeFiles(CProjectNode *pNode,CListViewCtrl *pListView) { unsigned int uiItemCount = 0; TCHAR szBuffer[16]; std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) { CItemData *pItemData = (*itFileObject); lsprintf(szBuffer,_T("%d"),uiItemCount + 1); pListView->AddItem(uiItemCount,0,szBuffer); pListView->AddItem(uiItemCount,1,pItemData->GetAudioData()->szTrackTitle); pListView->AddItem(uiItemCount,2,pItemData->GetAudioData()->szTrackArtist); pListView->SetItemData(uiItemCount,(DWORD_PTR)pItemData); uiItemCount++; } } /* CTreeManager::HasExtraAudioData ------------------------------- Returns true if all items in pNode contains both track title and artist information. */ bool CTreeManager::HasExtraAudioData(CProjectNode *pNode) { std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) { CItemData *pItemData = (*itFileObject); if (pItemData->GetAudioData()->szTrackArtist[0] == '\0' || pItemData->GetAudioData()->szTrackTitle[0] == '\0') { return false; } } return true; } void CTreeManager::SaveLocalNodeFileData(CXmlProcessor *pXml,CProjectNode *pNode, std::vector &FolderStack, unsigned int &uiFileCount,unsigned int uiRootLength) { // Save the item information. TCHAR szEntryName[32]; TCHAR szInternalName[MAX_PATH]; std::list ::iterator itNodeObject; for (itNodeObject = pNode->m_Children.begin(); itNodeObject != pNode->m_Children.end(); itNodeObject++) { FolderStack.push_back(*itNodeObject); CItemData *pItemData = (*itNodeObject)->pItemData; // Don't save imported items. if (pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) continue; lsprintf(szEntryName,_T("File%d"),uiFileCount++); pXml->AddElement(szEntryName,_T(""),true); pXml->AddElementAttr(_T("flags"),(int)pItemData->ucFlags); lstrcpy(szInternalName,pItemData->GetFilePath() + uiRootLength); lstrcat(szInternalName,pItemData->GetFileName()); pXml->AddElement(_T("InternalName"),szInternalName); pXml->AddElement(_T("FullPath"),pItemData->szFullPath); FILETIME LocalFileTime; DosDateTimeToFileTime(pItemData->usFileDate,pItemData->usFileTime,&LocalFileTime); ULARGE_INTEGER iLocalFileTime; memcpy(&iLocalFileTime,&LocalFileTime,sizeof(FILETIME)); pXml->AddElement(_T("FileTime"),(__int64)iLocalFileTime.QuadPart); pXml->LeaveElement(); } std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) { CItemData *pItemData = (*itFileObject); // Don't save imported items. if (pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) continue; lsprintf(szEntryName,_T("File%d"),uiFileCount++); pXml->AddElement(szEntryName,_T(""),true); pXml->AddElementAttr(_T("flags"),(int)pItemData->ucFlags); lstrcpy(szInternalName,pItemData->GetFilePath() + uiRootLength); lstrcat(szInternalName,pItemData->GetFileName()); pXml->AddElement(_T("InternalName"),szInternalName); pXml->AddElement(_T("FullPath"),pItemData->szFullPath); FILETIME LocalFileTime; DosDateTimeToFileTime(pItemData->usFileDate,pItemData->usFileTime,&LocalFileTime); ULARGE_INTEGER iLocalFileTime; memcpy(&iLocalFileTime,&LocalFileTime,sizeof(FILETIME)); pXml->AddElement(_T("FileTime"),(__int64)iLocalFileTime.QuadPart); pXml->LeaveElement(); } } void CTreeManager::SaveNodeFileData(CXmlProcessor *pXml,CProjectNode *pRootNode) { CProjectNode *pCurNode = pRootNode; unsigned int uiRootLength = lstrlen(pRootNode->pItemData->GetFilePath()) + lstrlen(pRootNode->pItemData->GetFileName()); // Save the information. unsigned int uiFileCount = 0; std::vector FolderStack; SaveLocalNodeFileData(pXml,pCurNode,FolderStack,uiFileCount,uiRootLength); while (FolderStack.size() > 0) { pCurNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); SaveLocalNodeFileData(pXml,pCurNode,FolderStack,uiFileCount,uiRootLength); } } void CTreeManager::SaveNodeAudioData(CXmlProcessor *pXml,CProjectNode *pRootNode) { unsigned int uiRootLength = lstrlen(pRootNode->pItemData->GetFilePath()) + lstrlen(pRootNode->pItemData->GetFileName()); // Save the information. unsigned int uiFileCount = 0; TCHAR szEntryName[32]; TCHAR szInternalName[MAX_PATH]; std::list ::iterator itFileObject; for (itFileObject = pRootNode->m_Files.begin(); itFileObject != pRootNode->m_Files.end(); itFileObject++) { CItemData *pItemData = (*itFileObject); lsprintf(szEntryName,_T("File%d"),uiFileCount++); pXml->AddElement(szEntryName,_T(""),true); lstrcpy(szInternalName,pItemData->GetFilePath() + uiRootLength); lstrcat(szInternalName,pItemData->GetFileName()); pXml->AddElement(_T("InternalName"),szInternalName); pXml->AddElement(_T("FullPath"),pItemData->szFullPath); if (pItemData->HasAudioData()) { pXml->AddElement(_T("TrackTitle"),pItemData->GetAudioData()->szTrackTitle); pXml->AddElement(_T("TrackArtist"),pItemData->GetAudioData()->szTrackArtist); } pXml->LeaveElement(); } } bool CTreeManager::LoadNodeFileData(CXmlProcessor *pXml,CProjectNode *pRootNode) { TCHAR szInternalName[MAX_PATH]; TCHAR szFullName[MAX_PATH]; for (unsigned int i = 0; i < pXml->GetElementChildCount(); i++) { if (!pXml->EnterElement(i)) return false; int iFlags = 0; pXml->GetSafeElementAttrValue(_T("flags"),&iFlags); // Temporary borrow the szFullName variable. It's safe. pXml->GetSafeElementData(_T("InternalName"),szFullName,MAX_PATH - 1); lstrcpy(szInternalName,pRootNode->pItemData->GetFilePath()); lstrcat(szInternalName,pRootNode->pItemData->GetFileName()); lstrcat(szInternalName,szFullName); pXml->GetSafeElementData(_T("FullPath"),szFullName,MAX_PATH - 1); // Check that the file exist. if (!(iFlags & PROJECTITEM_FLAG_ISFOLDER) && !ckcore::File::exist(szFullName)) { MessageBox(*g_pMainFrame,ckcore::string::formatstr(lngGetString(WARNING_MISSPROJFILE),szFullName).c_str(), lngGetString(GENERAL_WARNING),MB_OK | MB_ICONWARNING); pXml->LeaveElement(); continue; } // File time. ULARGE_INTEGER iLocalFileTime; __int64 iTemp = 0; pXml->GetSafeElementData(_T("FileTime"),&iTemp); iLocalFileTime.QuadPart = iTemp; FILETIME LocalFileTime; memcpy(&LocalFileTime,&iLocalFileTime,sizeof(FILETIME)); //if (bIsFolder) if (iFlags & PROJECTITEM_FLAG_ISFOLDER) { // Include a trailing backslash to indicate that we're dealing with a folder. TCHAR szTemp[MAX_PATH]; lstrcpy(szTemp,szInternalName); IncludeTrailingBackslash(szTemp); CProjectNode *pNode = AddPath(szTemp); pNode->pItemData->ucFlags = (unsigned char)iFlags; lstrcpy(pNode->pItemData->szFullPath,szFullName); // Copy the modified time. FileTimeToDosDateTime(&LocalFileTime, &pNode->pItemData->usFileDate, &pNode->pItemData->usFileTime); } else { CItemData *pItemData = new CItemData(); pItemData->ucFlags = (unsigned char)iFlags; // Paths. TCHAR *szFileNameBuffer = pItemData->BeginEditFileName(); lstrcpy(szFileNameBuffer,szInternalName); ExtractFileName(szFileNameBuffer); pItemData->EndEditFileName(); TCHAR *szFilePathBuffer = pItemData->BeginEditFilePath(); lstrcpy(szFilePathBuffer,szInternalName); if (!ExtractFilePath(szFilePathBuffer)) lstrcpy(szFilePathBuffer,_T("/")); pItemData->EndEditFilePath(); lstrcpy(pItemData->szFullPath,szFullName); // File type. SHFILEINFO shFileInfo; if (SHGetFileInfo(pItemData->GetFileName(),FILE_ATTRIBUTE_NORMAL,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_TYPENAME)) { lstrcpy(pItemData->szFileType,shFileInfo.szTypeName); } CProjectNode *pCurrentNode; if (pItemData->GetFilePath()[1] != '\0') // pData->szFilePath[1] == '\0' => pData->szFilePath = "\\" pCurrentNode = g_TreeManager.AddPath(szInternalName); else pCurrentNode = g_TreeManager.m_pRootNode; // Modified time. FileTimeToDosDateTime(&LocalFileTime,&pItemData->usFileDate,&pItemData->usFileTime); // Size. pItemData->uiSize = ckcore::File::size(szFullName); pCurrentNode->m_Files.push_back(pItemData); } pXml->LeaveElement(); } return true; } // FIXME: This function actually duplicates functionallity from the project manager. bool CTreeManager::LoadNodeAudioData(CXmlProcessor *pXml,CProjectNode *pRootNode, int iProjectType) { TCHAR szInternalName[MAX_PATH]; TCHAR szFullName[MAX_PATH]; for (unsigned int i = 0; i < pXml->GetElementChildCount(); i++) { if (!pXml->EnterElement(i)) return false; pXml->GetSafeElementData(_T("InternalName"),szInternalName,MAX_PATH - 1); pXml->GetSafeElementData(_T("FullPath"),szFullName,MAX_PATH - 1); CItemData *pItemData = new CItemData(); // Paths. TCHAR *szFileNameBuffer = pItemData->BeginEditFileName(); lstrcpy(szFileNameBuffer,szInternalName); ExtractFileName(szFileNameBuffer); pItemData->EndEditFileName(); TCHAR *szFilePathBuffer = pItemData->BeginEditFilePath(); lstrcpy(szFilePathBuffer,szInternalName); if (!ExtractFilePath(szFilePathBuffer)) lstrcpy(szFilePathBuffer,_T("/")); pItemData->EndEditFilePath(); lstrcpy(pItemData->szFullPath,szFullName); // Check that the file exist. if (!ckcore::File::exist(szFullName)) { MessageBox(*g_pMainFrame,ckcore::string::formatstr(lngGetString(WARNING_MISSPROJFILE),szFullName).c_str(), lngGetString(GENERAL_WARNING),MB_OK | MB_ICONWARNING); pXml->LeaveElement(); continue; } // Check file encoding. bool bEncoded = false; unsigned __int64 uiDuration = 0; // If the audio file is not a Wave file, try to find a codec that can handle it. if (GetAudioFormat(szFullName) != AUDIOFORMAT_WAVE) { // Audio file information. int iNumChannels = -1; int iSampleRate = -1; int iBitRate = -1; for (unsigned int i = 0; i < g_CodecManager.m_Codecs.size(); i++) { // We're only interested in decoders. if ((g_CodecManager.m_Codecs[i]->irc_capabilities() & IRC_HAS_DECODER) == 0) continue; if (g_CodecManager.m_Codecs[i]->irc_decode_init(szFullName,iNumChannels, iSampleRate,iBitRate,uiDuration)) { // Exit the decoder immediately since we don't want to decode the file yet. g_CodecManager.m_Codecs[i]->irc_decode_exit(); bEncoded = true; break; } } if (!bEncoded) { lngMessageBox(*g_pMainFrame,FAILURE_UNSUPAUDIO,GENERAL_ERROR,MB_OK | MB_ICONERROR); pXml->LeaveElement(); continue; } } // Track length. if (bEncoded) pItemData->GetAudioData()->uiTrackLength = uiDuration; else pItemData->GetAudioData()->uiTrackLength = GetAudioLength(szFullName); // Track size. if (iProjectType == PROJECTTYPE_MIXED) // Count using the Mode-1 sector size since the spacemeter in these projects are based on that disc size. pItemData->uiSize = (pItemData->GetAudioData()->uiTrackLength / 1000) * 75 * 2048; else pItemData->uiSize = pItemData->GetAudioData()->uiTrackLength; // Track information. if (pXml->EnterElement(_T("TrackTitle"))) { pXml->LeaveElement(); pXml->GetSafeElementData(_T("TrackTitle"),pItemData->GetAudioData()->szTrackTitle,159); // FIXME: Constant value?! } if (pXml->EnterElement(_T("TrackArtist"))) { pXml->LeaveElement(); pXml->GetSafeElementData(_T("TrackArtist"),pItemData->GetAudioData()->szTrackArtist,159); } pRootNode->m_Files.push_back(pItemData); pXml->LeaveElement(); } return true; } void CTreeManager::GetLocalPathList(ckfilesystem::FileSet &Files,CProjectNode *pNode, std::vector &FolderStack,int iPathStripLen) { TCHAR szInternalFilePath[MAX_PATH]; bool bHasChildren = false; std::list ::iterator itNodeObject; for (itNodeObject = pNode->m_Children.begin(); itNodeObject != pNode->m_Children.end(); itNodeObject++) { CItemData *pItemData = (*itNodeObject)->pItemData; // Skip imported folders. /*if (pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) continue;*/ bHasChildren = true; FolderStack.push_back(*itNodeObject); // Force slash delimiters (no backslash delimiters allowed). TCHAR *szFilePathBuffer = pItemData->BeginEditFilePath(); ForceSlashDelimiters(szFilePathBuffer + iPathStripLen); pItemData->EndEditFilePath(); ForceSlashDelimiters(pItemData->szFullPath); lstrcpy(szInternalFilePath,pItemData->GetFilePath() + iPathStripLen); lstrcat(szInternalFilePath,pItemData->GetFileName()); // Handle import data. unsigned char ucFlags = ckfilesystem::FileDescriptor::FLAG_DIRECTORY; void *pData = NULL; if (pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) { ucFlags |= ckfilesystem::FileDescriptor::FLAG_IMPORTED; pData = pItemData->GetIsoData(); } // If the insertion fails, the auto_ptr will automatically release the memory. std::auto_ptr< ckfilesystem::FileDescriptor > fd( new ckfilesystem::FileDescriptor( szInternalFilePath, pItemData->szFullPath, ucFlags, pData ) ); Files.insert( fd.get() ); fd.release(); } std::list ::iterator itFileObject; for (itFileObject = pNode->m_Files.begin(); itFileObject != pNode->m_Files.end(); itFileObject++) { CItemData *pItemData = (*itFileObject); // Skip imported files. /*if (pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) continue;*/ bHasChildren = true; // Force slash delimiters (no backslash delimiters allowed). TCHAR *szFilePathBuffer = pItemData->BeginEditFilePath(); ForceSlashDelimiters(szFilePathBuffer + iPathStripLen); pItemData->EndEditFilePath(); ForceSlashDelimiters(pItemData->szFullPath); lstrcpy(szInternalFilePath,pItemData->GetFilePath() + iPathStripLen); lstrcat(szInternalFilePath,pItemData->GetFileName()); // Handle import data. unsigned char ucFlags = 0; void *pData = NULL; if (pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) { ucFlags |= ckfilesystem::FileDescriptor::FLAG_IMPORTED; pData = pItemData->GetIsoData(); } // If the insertion fails, the auto_ptr will automatically release the memory. std::auto_ptr< ckfilesystem::FileDescriptor > fd( new ckfilesystem::FileDescriptor( szInternalFilePath, pItemData->szFullPath, ucFlags, pData ) ); Files.insert( fd.get() ); fd.release(); } // If the folder does not have children, add it manually. if (!bHasChildren) { // Force slash delimiters (no backslash delimiters allowed). TCHAR *szFilePathBuffer = pNode->pItemData->BeginEditFilePath(); ForceSlashDelimiters(szFilePathBuffer + iPathStripLen); pNode->pItemData->EndEditFilePath(); ForceSlashDelimiters(pNode->pItemData->szFullPath); lstrcpy(szInternalFilePath,pNode->pItemData->GetFilePath() + iPathStripLen); lstrcat(szInternalFilePath,pNode->pItemData->GetFileName()); // Copy the file name of a temporary empty directory. TCHAR szEmptyFolder[MAX_PATH]; lstrcpy(szEmptyFolder,g_TempManager.GetEmtpyDirectory()); ForceSlashDelimiters(szEmptyFolder); // Handle import data. unsigned char ucFlags = ckfilesystem::FileDescriptor::FLAG_DIRECTORY; void *pData = NULL; if (pNode->pItemData->ucFlags & PROJECTITEM_FLAG_ISIMPORTED) { ucFlags |= ckfilesystem::FileDescriptor::FLAG_IMPORTED; pData = pNode->pItemData->GetIsoData(); } // If the insertion fails, the auto_ptr will automatically release the memory. std::auto_ptr< ckfilesystem::FileDescriptor > fd( new ckfilesystem::FileDescriptor( szInternalFilePath, szEmptyFolder, ucFlags, pData ) ); Files.insert( fd.get() ); fd.release(); } } void CTreeManager::GetPathList(ckfilesystem::FileSet &Files,CProjectNode *pRootNode,int iPathStripLen) { CProjectNode *pCurNode = pRootNode; // Save the information. std::vector FolderStack; GetLocalPathList(Files,pCurNode,FolderStack,iPathStripLen); while (FolderStack.size() > 0) { pCurNode = FolderStack[FolderStack.size() - 1]; FolderStack.pop_back(); GetLocalPathList(Files,pCurNode,FolderStack,iPathStripLen); } } void CTreeManager::ImportLocalIsoTree(ckfilesystem::IsoTreeNode *pLocalIsoNode, CProjectNode *pLocalNode, std::vector > &FolderStack) { std::vector::const_iterator itIsoNode; for (itIsoNode = pLocalIsoNode->children_.begin(); itIsoNode != pLocalIsoNode->children_.end(); itIsoNode++) { if ((*itIsoNode)->file_flags_ & DIRRECORD_FILEFLAG_DIRECTORY) { // Try to locate the corresponding project node. CProjectNode *pCurNode = NULL; std::list::const_iterator itNode; for (itNode = pLocalNode->m_Children.begin(); itNode != pLocalNode->m_Children.end(); itNode++) { if (!lstrcmpi((*itNode)->pItemData->GetFileName(),(*itIsoNode)->file_name_.c_str())) { pCurNode = *itNode; break; } } // Create a new node if necessary. if (pCurNode == NULL) { pCurNode = new CProjectNode(pLocalNode); pCurNode->pItemData->ucFlags |= PROJECTITEM_FLAG_ISIMPORTED; pCurNode->pItemData->SetFileName((*itIsoNode)->file_name_.c_str()); TCHAR *szFilePath = pCurNode->pItemData->BeginEditFilePath(); lstrcpy(szFilePath,pLocalNode->pItemData->GetFilePath()); lstrcat(szFilePath,pLocalNode->pItemData->GetFileName()); lstrcat(szFilePath,_T("/")); pCurNode->pItemData->EndEditFilePath(); ckfilesystem::iso_make_dosdatetime((*itIsoNode)->rec_timestamp_, pCurNode->pItemData->usFileDate, pCurNode->pItemData->usFileTime); // Force a folder icon to be used. SHFILEINFO shFileInfo; if (SHGetFileInfo(_T(""),FILE_ATTRIBUTE_DIRECTORY,&shFileInfo, sizeof(shFileInfo),SHGFI_USEFILEATTRIBUTES | SHGFI_SYSICONINDEX | SHGFI_TYPENAME)) { pCurNode->iIconIndex = shFileInfo.iIcon; lstrcpy(pCurNode->pItemData->szFileType,shFileInfo.szTypeName); } // Add ISO9660 data. CItemData::CIsoData *pIsoData = pCurNode->pItemData->GetIsoData(); pIsoData->file_flags_ = (*itIsoNode)->file_flags_; pIsoData->file_unit_size_ = (*itIsoNode)->file_unit_size_; pIsoData->interleave_gap_size_ = (*itIsoNode)->interleave_gap_size_; pIsoData->volseq_num_ = (*itIsoNode)->volseq_num_; pIsoData->extent_loc_ = (*itIsoNode)->extent_loc_; pIsoData->extent_len_ = (*itIsoNode)->extent_len_; memcpy(&pIsoData->rec_timestamp_,&(*itIsoNode)->rec_timestamp_, sizeof(ckfilesystem::tiso_dir_record_datetime)); // Finalize. pLocalNode->m_Children.push_back(pCurNode); AddTreeNode(pLocalNode->m_hTreeItem,pCurNode); } FolderStack.push_back(std::make_pair(*itIsoNode,pCurNode)); } else { CItemData *pItemData = new CItemData(); pItemData->ucFlags |= PROJECTITEM_FLAG_ISIMPORTED; pItemData->uiSize = (*itIsoNode)->extent_len_; pItemData->SetFileName((*itIsoNode)->file_name_.c_str()); TCHAR *szFilePath = pItemData->BeginEditFilePath(); lstrcpy(szFilePath,pLocalNode->pItemData->GetFilePath()); lstrcat(szFilePath,pLocalNode->pItemData->GetFileName()); lstrcat(szFilePath,_T("/")); pItemData->EndEditFilePath(); ckfilesystem::iso_make_dosdatetime((*itIsoNode)->rec_timestamp_, pItemData->usFileDate,pItemData->usFileTime); // Add ISO9660 data. CItemData::CIsoData *pIsoData = pItemData->GetIsoData(); pIsoData->file_flags_ = (*itIsoNode)->file_flags_; pIsoData->file_unit_size_ = (*itIsoNode)->file_unit_size_; pIsoData->interleave_gap_size_ = (*itIsoNode)->interleave_gap_size_; pIsoData->volseq_num_ = (*itIsoNode)->volseq_num_; pIsoData->extent_loc_ = (*itIsoNode)->extent_loc_; pIsoData->extent_len_ = (*itIsoNode)->extent_len_; memcpy(&pIsoData->rec_timestamp_,&(*itIsoNode)->rec_timestamp_, sizeof(ckfilesystem::tiso_dir_record_datetime)); // Finalize. pLocalNode->m_Files.push_back(pItemData); } } } void CTreeManager::ImportIsoTree(ckfilesystem::IsoTreeNode *pIsoRootNode,CProjectNode *pRootNode) { // Save the information. std::vector > FolderStack; ImportLocalIsoTree(pIsoRootNode,pRootNode,FolderStack); while (FolderStack.size() > 0) { ckfilesystem::IsoTreeNode *pIsoNode = FolderStack.back().first; CProjectNode *pNode = FolderStack.back().second; FolderStack.pop_back(); ImportLocalIsoTree(pIsoNode,pNode,FolderStack); } } ================================================ FILE: src/app/tree_manager.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include #include #include #include #include #define PROJECTITEM_FLAG_ISFOLDER 1 #define PROJECTITEM_FLAG_ISLOCKED 2 #define PROJECTITEM_FLAG_ISIMPORTED 4 #define PROJECTITEM_FLAG_ISDVDVIDEO 8 #define PROJECTITEM_FLAG_ISPROJECTROOT 16 class CProjectNode; // This structure represents a file (or folder) inside the project view. class CItemData { public: class CAudioData { public: unsigned __int64 uiTrackLength; TCHAR szTrackTitle[160]; TCHAR szTrackArtist[160]; CAudioData() { uiTrackLength = 0; szTrackTitle[0] = '\0'; szTrackArtist[0] = '\0'; } }; typedef ckfilesystem::IsoImportData CIsoData; private: TCHAR m_szFileName[MAX_PATH]; // File name in the project (disc image). TCHAR m_szFilePath[MAX_PATH]; // File path in the project (disc image). void FileNameChanged(); void FilePathChanged(); // Only allocated when needed. CAudioData *m_pAudioData; CIsoData *m_pIsoData; public: CItemData(); ~CItemData(); //TCHAR szFileName[MAX_PATH]; // File name in the project (disc image). //TCHAR szFilePath[MAX_PATH]; // File path in the project (disc image). TCHAR szFullPath[MAX_PATH]; // Real file path on the harddrive. TCHAR szFileType[80]; unsigned short usFileDate; unsigned short usFileTime; unsigned __int64 uiSize; // In data and mixed-mode projects this // variable holds the file size in bytes. // In audio projects it holds the same // information as uiTrackLength. // Only used in audio mode. Audio track length in milliseconds. // UPDATE: An object with this information is only created when needed. /*unsigned __int64 uiTrackLength; TCHAR szTrackTitle[160]; TCHAR szTrackArtist[160];*/ unsigned char ucFlags; // Getters and setters. void SetFileName(const TCHAR *szFileName); const TCHAR *GetFileName(); void SetFilePath(const TCHAR *szFilePath); const TCHAR *GetFilePath(); TCHAR *BeginEditFileName(); void EndEditFileName(); TCHAR *BeginEditFilePath(); void EndEditFilePath(); bool HasAudioData(); CAudioData *GetAudioData(); bool HasIsoData(); CIsoData *GetIsoData(); }; class CProjectNode { public: std::list m_Children; std::list m_Files; CProjectNode *m_pParent; CItemData *pItemData; int iIconIndex; HTREEITEM m_hTreeItem; CProjectNode(CProjectNode *pParent) { m_pParent = pParent; m_hTreeItem = NULL; // Initialize the default data. pItemData = new CItemData(); pItemData->ucFlags = PROJECTITEM_FLAG_ISFOLDER; } ~CProjectNode() { delete pItemData; // Free the children. std::list ::iterator itNodeObject; for (itNodeObject = m_Children.begin(); itNodeObject != m_Children.end(); itNodeObject++) delete *itNodeObject; m_Children.clear(); // Free the file data. std::list ::iterator itFileObject; for (itFileObject = m_Files.begin(); itFileObject != m_Files.end(); itFileObject++) delete *itFileObject; m_Files.clear(); } void Sort(unsigned int uiSortColumn,bool bSortUp,bool bSortAudio); }; class CChildComparator { private: unsigned int m_uiSortColumn; bool m_bSortUp; bool m_bSortAudio; public: CChildComparator(unsigned int uiSortColumn,bool bSortUp,bool bSortAudio) { m_uiSortColumn = uiSortColumn; m_bSortUp = bSortUp; m_bSortAudio = bSortAudio; } bool operator() (const CProjectNode *pSafeNode1,const CProjectNode *pSafeNode2); }; class CFileComparator { private: unsigned int m_uiSortColumn; bool m_bSortUp; bool m_bSortAudio; public: CFileComparator(unsigned int uiSortColumn,bool bSortUp,bool bSortAudio) { m_uiSortColumn = uiSortColumn; m_bSortUp = bSortUp; m_bSortAudio = bSortAudio; } bool operator() (const CItemData *pSafeItemData1,const CItemData *pSafeItemData2); }; class CTreeManager { private: CTreeViewCtrlEx *m_pTreeView; CListViewCtrl *m_pListView; CProjectNode *m_pRootNode; CProjectNode *m_pCurrentNode; TCHAR m_szCurrentPath[MAX_PATH]; HTREEITEM GetTreeChildFromParent(HTREEITEM hParentItem,TCHAR *szText); bool HasChildren(HTREEITEM hItem,bool bHasChildren); CProjectNode *GetDirFromParent(CProjectNode *pParent,const TCHAR *szName); CProjectNode *NodalizePath(const TCHAR *szPath); CProjectNode *GetChildFromParent(CProjectNode *pParentNode,const TCHAR *szText); void ListNode(CProjectNode *pNode); void RebuildLocalPaths(CProjectNode *pNode,std::vector &FolderStack); unsigned __int64 GetLocalSizeFromNode(CProjectNode *pNode,std::vector &FolderStack); void SaveLocalNodeFileData(CXmlProcessor *pXml,CProjectNode *pNode, std::vector &FolderStack,unsigned int &uiFileCount, unsigned int uiRootLength); void GetLocalPathList(ckfilesystem::FileSet &Files,CProjectNode *pNode, std::vector &FolderStack,int iPathStripLen); void GetLocalNodeContents(CProjectNode *pNode,std::vector &FolderStack, unsigned __int64 &uiFileCount,unsigned __int64 &uiNodeCount); void RecursiveLocalSetFlags(CProjectNode *pNode,std::vector &FolderStack, unsigned char ucFlags); public: CTreeManager(); ~CTreeManager(); void AssignControls(CTreeViewCtrlEx *pTreeView,CListViewCtrl *pListView); void CreateTree(const TCHAR *szRootName,int iImage); void DestroyTree(); HTREEITEM AddTreeNode(HTREEITEM hParentItem,CProjectNode *pNode); CProjectNode *AddPath(const TCHAR *szPath); CProjectNode *InsertVirtualRoot(const TCHAR *szNodeName,int iImage); void SelectPath(const TCHAR *szPath); void Refresh(); void RebuildPaths(const TCHAR *szStartPath); bool RemoveEntry(CProjectNode *pNode); bool RemoveEntry(CProjectNode *pNode,CItemData *pItemData); bool RemoveEntry(const TCHAR *szLocalPath,const TCHAR *szFullPath); bool MoveEntry(CProjectNode *pParent,CItemData *pItemData,CProjectNode *pNewParent); bool IsSubNode(CProjectNode *pNode1,CProjectNode *pNode2); CItemData *GetChildItem(CProjectNode *pParent,const TCHAR *szName); CProjectNode *GetChildNode(CProjectNode *pParent,const TCHAR *szName); CProjectNode *ResolveNode(CProjectNode *pParent,CItemData *pNodeItem); void GetCurrentPath(TCHAR *szCurrentPath); void SetCurrentPath(const TCHAR *szCurrentPath); CProjectNode *GetCurrentNode(); CProjectNode *GetRootNode(); CProjectNode *GetDirFromParent(CProjectNode *pParent,TCHAR *szText); CProjectNode *GetNodeFromPath(const TCHAR *szPath); unsigned __int64 GetNodeSize(CProjectNode *pNode); unsigned __int64 GetNodeSize(CProjectNode *pParentNode,CItemData *pItemData); void GetNodeContents(CProjectNode *pRootNode,unsigned __int64 &uiFileCount, unsigned __int64 &uiNodeCount); void RecursiveSetFlags(CProjectNode *pRootNode,unsigned char ucFlags); void DeleteImportedItems(CProjectNode *pRootNode); void GetNodeFullPaths(CProjectNode *pRootNode,std::vector &FullPaths); void GetNodeFiles(CProjectNode *pNode,std::vector &Files); void ListNodeFiles(CProjectNode *pNode,CListViewCtrl *pListView); bool HasExtraAudioData(CProjectNode *pNode); // Save/load routines. void SaveNodeFileData(CXmlProcessor *pXml,CProjectNode *pRootNode); void SaveNodeAudioData(CXmlProcessor *pXml,CProjectNode *pRootNode); bool LoadNodeFileData(CXmlProcessor *pXml,CProjectNode *pRootNode); bool LoadNodeAudioData(CXmlProcessor *pXml,CProjectNode *pRootNode,int iProjectType); void GetPathList(ckfilesystem::FileSet &Files,CProjectNode *pRootNode,int iPathStripLen = 0); void ImportLocalIsoTree(ckfilesystem::IsoTreeNode *pLocalIsoNode,CProjectNode *pLocalNode, std::vector > &FolderStack); void ImportIsoTree(ckfilesystem::IsoTreeNode *pIsoRootNode,CProjectNode *pRootNode); }; extern CTreeManager g_TreeManager; ================================================ FILE: src/app/utility/audio_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "audio_util.hh" bool IsWave(const TCHAR *szFileName) { ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_READ)) return false; // Validate ID. char szBuffer[4]; if (File.read(szBuffer,4) == -1) return false; if (strncmp(szBuffer,"RIFF",4)) return false; // Ignore size. File.seek(4,ckcore::File::ckFILE_CURRENT); // Validate type. if (File.read(szBuffer,4) == -1) return false; if (strncmp(szBuffer,"WAVE",4)) return false; return true; } int GetAudioFormat(const TCHAR *szFileName) { if (IsWave(szFileName)) return AUDIOFORMAT_WAVE; return AUDIOFORMAT_UNKNOWN; } int GetAudioLength(const TCHAR *szFileName) { TCHAR szCommand[MAX_PATH + 33],szResult[256],szLength[256]; int iLength = 0; lsprintf(szCommand,_T("open \"%s\" type waveaudio alias seq"),szFileName); mciSendString(szCommand,szResult,256,NULL); mciSendString(_T("status seq length"),szLength,256,NULL); mciSendString(_T("close seq"),szResult,255,NULL); return _wtoi(szLength); } /*int GetAudioInfo(const TCHAR *szFileName) { HANDLE hFile = fs_open(szFileName,_T("rb")); if (hFile == INVALID_HANDLE_VALUE) return false; // Header chunk. char szBuffer[4]; fs_read(szBuffer,4,hFile); if (strncmp(szBuffer,"RIFF",4)) { fs_close(hFile); return AUDIOLENGTH_BADFORMAT; } fs_seek(hFile,4,FILE_CURRENT); fs_read(szBuffer,4,hFile); if (strncmp(szBuffer,"WAVE",4)) { fs_close(hFile); return AUDIOLENGTH_BADFORMAT; } // Format chunk. fs_read(szBuffer,4,hFile); if (strncmp(szBuffer,"fmt ",4)) { fs_close(hFile); return AUDIOLENGTH_BADFORMAT; } unsigned long ulSize = 0; fs_read(&ulSize,sizeof(unsigned long),hFile); unsigned short usCompCode = 0; unsigned short usNumChannels = 0; unsigned long ulSampleRate = 0; unsigned long ulBytesPerSec = 0; unsigned short usBlockAlign = 0; unsigned short usBitsPerSample = 0; fs_read(&usCompCode,sizeof(unsigned short),hFile); fs_read(&usNumChannels,sizeof(unsigned short),hFile); fs_read(&ulSampleRate,sizeof(unsigned long),hFile); fs_read(&ulBytesPerSec,sizeof(unsigned long),hFile); fs_read(&usBlockAlign,sizeof(unsigned short),hFile); fs_read(&usBitsPerSample,sizeof(unsigned short),hFile); fs_close(hFile); return AUDIOLENGTH_BADFORMAT; }*/ ================================================ FILE: src/app/utility/audio_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #define AUDIOFORMAT_UNKNOWN 0 #define AUDIOFORMAT_WAVE 1 #define AUDIOLENGTH_BADFORMAT 0 int GetAudioFormat(const TCHAR *szFileName); int GetAudioLength(const TCHAR *szFileName); //int GetAudioInfo(const TCHAR *szFileName); ================================================ FILE: src/app/utility/device_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "device_util.hh" namespace NDeviceUtil { /** * Convert the address of the specified device into string form making * it compatible with command line usage of the back-end applications. * @param [in] device The device to obtain the address from. * @return The address in command line string form. */ ckcore::tstring GetDeviceAddr(const ckmmc::Device &device) { const ckmmc::Device::Address &addr = device.address(); #ifdef USE_CDRKIT return addr.device_; #else ckcore::tchar buffer[64]; ckcore::convert::sprintf(buffer,sizeof(buffer),ckT("%d,%d,%d"), addr.bus_,addr.target_,addr.lun_); return buffer; #endif } /** * Convert the address of the specified device into string form making * it compatible with command line usage of the back-end applications. * @param [in] device The device to obtain the address from. * @return The address in command line string form. */ std::string GetDeviceAddrA(const ckmmc::Device &device) { const ckmmc::Device::Address &addr = device.address(); #ifdef USE_CDRKIT return addr.device_; #else char buffer[64]; sprintf(buffer,"%d,%d,%d",addr.bus_,addr.target_,addr.lun_); return buffer; #endif } ckcore::tstring GetDeviceName(const ckmmc::Device &device) { const ckmmc::Device::Address &addr = device.address(); return addr.device_ + ckT(": ") + device.name(); } }; ================================================ FILE: src/app/utility/device_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include namespace NDeviceUtil { ckcore::tstring GetDeviceAddr(const ckmmc::Device &device); std::string GetDeviceAddrA(const ckmmc::Device &device); ckcore::tstring GetDeviceName(const ckmmc::Device &device); }; ================================================ FILE: src/app/utility/lang_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "settings.hh" #include "string_table.hh" #include "lang_util.hh" const TCHAR *g_szHelpFile = _T("InfraRecorder.chm"); const TCHAR *lngGetString(unsigned int uiID) { ATLASSERT( uiID < _countof(g_szStringTable) ); // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("strings"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(uiID,szStrValue)) return szStrValue; } } // Load internal (English) string. return g_szStringTable[uiID]; } const TCHAR *lngGetManual() { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("translation"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(TRANSLATION_ID_MANUAL,szStrValue)) return szStrValue; } } // Return default file name. return g_szHelpFile; } int lngMessageBox(HWND hWnd,unsigned int uiTextID,unsigned int uiCaptionID,unsigned int uiType) { return MessageBox(hWnd,lngGetString(uiTextID),lngGetString(uiCaptionID),uiType); } void lngTranslateTables() { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a strings translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("filesystem"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::WARNING_FSDIRLEVEL,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::WARNING_FSDIRLEVEL,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::WARNING_SKIPFILE,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::WARNING_SKIPFILE,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::WARNING_SKIP4GFILE,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::WARNING_SKIP4GFILE,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::WARNING_SKIP4GFILEISO,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::WARNING_SKIP4GFILEISO,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::ERROR_PATHTABLESIZE,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::ERROR_PATHTABLESIZE,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::ERROR_OPENWRITE,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::ERROR_OPENWRITE,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::ERROR_OPENREAD,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::ERROR_OPENREAD,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::STATUS_BUILDTREE,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::STATUS_BUILDTREE,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::STATUS_WRITEDATA,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::STATUS_WRITEDATA,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::STATUS_WRITEISOTABLE,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::STATUS_WRITEISOTABLE,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::STATUS_WRITEJOLIETTABLE,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::STATUS_WRITEJOLIETTABLE,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::STATUS_WRITEDIRENTRIES,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::STATUS_WRITEDIRENTRIES,szStrValue); if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(ckfilesystem::StringTable::ERROR_DVDVIDEO,szStrValue)) ckfilesystem::StringTable::instance().set_string(ckfilesystem::StringTable::ERROR_DVDVIDEO,szStrValue); } } } ckcore::tstring lngSlowFormatStr(const eStringTable TranslatedFormatStr,...) { ckcore::tstring Result; va_list Args; va_start(Args,TranslatedFormatStr); ckcore::string::vformatstr(Result,lngGetString(TranslatedFormatStr),Args); va_end(Args); return Result; } ================================================ FILE: src/app/utility/lang_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #define TRANSLATION_ID_AUTHOR 1 #define TRANSLATION_ID_DATE 2 #define TRANSLATION_ID_VERSION 3 #define TRANSLATION_ID_MANUAL 4 const TCHAR *lngGetString(unsigned int uiID); const TCHAR *lngGetManual(); int lngMessageBox(HWND hWnd,unsigned int uiTextID,unsigned int uiCaptionID,unsigned int uiType); void lngTranslateTables(); ckcore::tstring lngSlowFormatStr(const eStringTable TranslatedFormatStr,...); ================================================ FILE: src/app/utility/shell_ext_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "shell_ext_util.hh" #include bool ExecShellExtFunction(const char *szFunctionName) { // Calculate file path. TCHAR szFileName[MAX_PATH]; ::GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,_T("shell.dll")); // Load library. HINSTANCE hInstance = LoadLibrary(szFileName); if (!hInstance) return false; // Call the function. HRESULT (STDAPICALLTYPE* pfn)(); (FARPROC&) pfn = GetProcAddress(hInstance,szFunctionName); if (pfn == NULL) { FreeLibrary(hInstance); return false; } if (FAILED(pfn())) { FreeLibrary(hInstance); return false; } FreeLibrary(hInstance); return true; } /* RegisterShellExtension ---------------------- Registers the shell extension. */ bool RegisterShellExtension() { return ExecShellExtFunction("DllRegisterServer"); } /* RegisterShellExtension ---------------------- Unregisters the shell extension. */ bool UnregisterShellExtension() { return ExecShellExtFunction("DllUnregisterServer"); } /* IsShellExtensionRegistered -------------------------- Returns true if the shell extension is registered with the system, it returns false otherwise. */ bool IsShellExtensionRegistered() { CRegistry Reg; Reg.SetRoot(HKEY_CLASSES_ROOT); if (Reg.OpenKey(_T("AppID\\shell.DLL"),false)) { TCHAR szAppID[39]; if (Reg.ReadString(_T("AppID"),szAppID,39 * sizeof(TCHAR))) { Reg.CloseKey(); if (!lstrcmp(szAppID,_T(IRSHELL_APPID))) return true; } Reg.CloseKey(); return false; } return false; } /* InstallExtension ---------------- Associates a file extension with the shell extension. */ bool InstallExtension(const TCHAR *szFileExt,CRegistry *pReg) { if (pReg->OpenKey(szFileExt)) { TCHAR szKeyName[64]; // If no key is specified we create our own. if (!pReg->ReadString(_T(""),szKeyName,64 * sizeof(TCHAR)) || !lstrcmp(szKeyName,_T(""))) { // Extension key name. lstrcpy(szKeyName,_T("iriso")); if (!pReg->WriteString(_T(""),szKeyName,64 * sizeof(TCHAR))) { pReg->CloseKey(); return false; } pReg->CloseKey(); // Key name description. if (!pReg->OpenKey(_T("iriso"),true)) return false; if (!pReg->WriteString(_T(""),_T("InfraRecorder disc image"),25 * sizeof(TCHAR))) { pReg->CloseKey(); return false; } } // Open key name and install shell extension. pReg->CloseKey(); TCHAR szFullName[256]; lstrcpy(szFullName,szKeyName), lstrcat(szFullName,_T("\\ShellEx\\ContextMenuHandlers\\Shell")); if (!pReg->OpenKey(szFullName)) return false; if (!pReg->WriteString(_T(""),_T(IRSHELL_GUID),38 * sizeof(TCHAR))) { pReg->CloseKey(); return false; } pReg->CloseKey(); return true; } return false; } bool InstallProjectExtension(CRegistry *pReg) { if (pReg->OpenKey(_T(".irp"))) { TCHAR szKeyName[64]; // If no key is specified we create our own. if (!pReg->ReadString(_T(""),szKeyName,64 * sizeof(TCHAR)) || !lstrcmp(szKeyName,_T(""))) { // Extension key name. lstrcpy(szKeyName,_T("irproject")); if (!pReg->WriteString(_T(""),szKeyName,64 * sizeof(TCHAR))) { pReg->CloseKey(); return false; } pReg->CloseKey(); // Key name description. if (!pReg->OpenKey(_T("irproject"),true)) return false; if (!pReg->WriteString(_T(""),_T("InfraRecorder project"),25 * sizeof(TCHAR))) { pReg->CloseKey(); return false; } } // Open key name and install shell extension. pReg->CloseKey(); TCHAR szFullName[256]; lstrcpy(szFullName,szKeyName), lstrcat(szFullName,_T("\\ShellEx\\ContextMenuHandlers\\Shell")); if (!pReg->OpenKey(szFullName)) return false; if (!pReg->WriteString(_T(""),_T(IRSHELL_GUID),38 * sizeof(TCHAR))) { pReg->CloseKey(); return false; } pReg->CloseKey(); return true; } return false; } /* UninstallExtension ------------------ Removes the association of a file extension with the shell extension. */ bool UninstallExtension(const TCHAR *szFileExt,CRegistry *pReg) { if (!pReg->OpenKey(szFileExt,false)) return true; TCHAR szKeyName[64]; if (pReg->ReadString(_T(""),szKeyName,64 * sizeof(TCHAR))) { pReg->CloseKey(); if (lstrcmp(szKeyName,_T(""))) { TCHAR szFullName[256]; lstrcpy(szFullName,szKeyName), lstrcat(szFullName,_T("\\ShellEx\\ContextMenuHandlers")); if (!pReg->OpenKey(szFullName,false)) return false; bool bResult = pReg->DeleteKey(_T("Shell")); pReg->CloseKey(); return bResult; } } return true; } /* IsExtensionInstalled -------------------- Returns true if the shell extension is associated with the speicifed file extension, otherwise it returns false. */ bool IsExtensionInstalled(const TCHAR *szFileExt,CRegistry *pReg) { if (!pReg->OpenKey(szFileExt,false)) return false; TCHAR szKeyName[64]; if (pReg->ReadString(_T(""),szKeyName,64 * sizeof(TCHAR))) { pReg->CloseKey(); if (lstrcmp(szKeyName,_T(""))) { TCHAR szFullName[256]; lstrcpy(szFullName,szKeyName), lstrcat(szFullName,_T("\\ShellEx\\ContextMenuHandlers\\Shell")); if (!pReg->OpenKey(szFullName,false)) return false; pReg->CloseKey(); return true; } } return false; } ================================================ FILE: src/app/utility/shell_ext_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "registry.hh" #define IRSHELL_APPID "{8E8DAC3C-E7C5-4495-9903-430C1F38CF86}" #define IRSHELL_GUID "{7022C5BB-445E-4300-99F2-0B7EDA907A53}" bool RegisterShellExtension(); bool UnregisterShellExtension(); bool IsShellExtensionRegistered(); bool InstallExtension(const TCHAR *szFileExt,CRegistry *pReg); bool InstallProjectExtension(CRegistry *pReg); bool UninstallExtension(const TCHAR *szFileExt,CRegistry *pReg); bool IsExtensionInstalled(const TCHAR *szFileExt,CRegistry *pReg); ================================================ FILE: src/app/utility/trans_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "trans_util.hh" /* UpdateStaticWidth ----------------- Updates the width of the specified static control so it fits the specified text. The function return the right end position of the static control. */ int UpdateStaticWidth(HWND hParentWnd,HWND hCtrlWnd,const TCHAR *szText) { // Calculate text width using the default system font. HDC hDC = GetDC(hParentWnd); HFONT hOldFont = (HFONT)::SelectObject(hDC,AtlGetDefaultGuiFont()); RECT rcText = { 0 }; ::DrawText(hDC,szText,lstrlen(szText),&rcText,DT_LEFT | DT_CALCRECT | DT_SINGLELINE); ::SelectObject(hDC,hOldFont); ::ReleaseDC(hParentWnd,hDC); if (rcText.right < 75) return -1; // Get static rectangle. RECT rcStatic = { 0 }; ::GetWindowRect(hCtrlWnd,&rcStatic); ::ScreenToClient(hParentWnd,(LPPOINT)&rcStatic); ::ScreenToClient(hParentWnd,((LPPOINT)&rcStatic) + 1); // Update static rectangle. rcStatic.right = rcStatic.left + rcText.right + TRANSUTIL_STATICEDIT_SPACING; ::MoveWindow(hCtrlWnd,rcStatic.left,rcStatic.top,rcStatic.right - rcStatic.left,rcStatic.bottom - rcStatic.top,TRUE); return rcStatic.right; } int UpdateStaticWidth(HWND hParentWnd,int iStaticID,const TCHAR *szText) { return UpdateStaticWidth(hParentWnd,GetDlgItem(hParentWnd,iStaticID),szText); } /* UpdateEditPos ------------- Updates the left position of the specified edit control. If bMove is set to true the edit control will be moved (the right position will be updated as well). */ void UpdateEditPos(HWND hParentWnd,int iEditID,int iLeft,bool bMove) { RECT rcEdit = { 0 }; ::GetWindowRect(::GetDlgItem(hParentWnd,iEditID),&rcEdit); ::ScreenToClient(hParentWnd,(LPPOINT)&rcEdit); ::ScreenToClient(hParentWnd,((LPPOINT)&rcEdit) + 1); int iDiff = rcEdit.left - iLeft; rcEdit.left = iLeft; ::MoveWindow(::GetDlgItem(hParentWnd,iEditID),rcEdit.left, rcEdit.top,rcEdit.right - rcEdit.left - (bMove ? iDiff : 0), rcEdit.bottom - rcEdit.top,TRUE); } int UpdateStaticHeight(HWND hParentWnd,int iStaticID,const TCHAR *szText) { RECT rcStatic = { 0 }; ::GetWindowRect(::GetDlgItem(hParentWnd,iStaticID),&rcStatic); ::ScreenToClient(hParentWnd,(LPPOINT)&rcStatic); ::ScreenToClient(hParentWnd,((LPPOINT)&rcStatic) + 1); HDC hDC = GetDC(hParentWnd); HFONT hOldFont = (HFONT)::SelectObject(hDC,AtlGetDefaultGuiFont()); RECT rcText = { 0 }; rcText.right = rcStatic.right - rcStatic.left; int iTextHeight = DrawText(hDC,szText,lstrlen(szText),&rcText,DT_LEFT | DT_CALCRECT | DT_WORDBREAK); int iDiff = iTextHeight - (rcStatic.bottom - rcStatic.top); if (iDiff > 0) ::MoveWindow(::GetDlgItem(hParentWnd,iStaticID),rcStatic.left,rcStatic.top,rcStatic.right - rcStatic.left,iTextHeight,TRUE); ::SelectObject(hDC,hOldFont); ::ReleaseDC(hParentWnd,hDC); return iDiff; } ================================================ FILE: src/app/utility/trans_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #define TRANSUTIL_STATICEDIT_SPACING 6 int UpdateStaticWidth(HWND hParentWnd,HWND hCtrlWnd,const TCHAR *szText); int UpdateStaticWidth(HWND hParentWnd,int iStaticID,const TCHAR *szText); void UpdateEditPos(HWND hParentWnd,int iEditID,int iLeft,bool bMove = false); int UpdateStaticHeight(HWND hParentWnd,int iStaticID,const TCHAR *szText); ================================================ FILE: src/app/version.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "version.hh" #ifdef VERSION_COMPATIBILITY_CHECK CWinVer g_WinVer; #pragma comment(lib,"Version.lib") CWinVer::CWinVer() { m_ulMajorVersion = 0; m_ulMinorVersion = 0; m_ulMajorIEVersion = 0; m_ulMinorIEVersion = 0; // Get Windows version information. OSVERSIONINFO ovInfo; ovInfo.dwOSVersionInfoSize = sizeof(OSVERSIONINFO); if (GetVersionEx(&ovInfo)) { m_ulMajorVersion = ovInfo.dwMajorVersion; m_ulMinorVersion = ovInfo.dwMinorVersion; } // Get Internet Explorer version information. VS_FIXEDFILEINFO *wxFileInfo; unsigned long ulDummy,ulVersionSize = GetFileVersionInfoSize(_T("shlwapi.dll"),NULL); if (ulVersionSize > 0) { unsigned char *pBuffer = new unsigned char[ulVersionSize]; if (GetFileVersionInfo(_T("shlwapi.dll"),NULL,ulVersionSize,pBuffer)) { if (VerQueryValue(pBuffer,_T("\\"),(void **)&wxFileInfo,(unsigned int *)&ulDummy)) { m_ulMajorIEVersion = wxFileInfo->dwFileVersionMS/65536; m_ulMinorIEVersion = wxFileInfo->dwFileVersionMS%65536; } } delete [] pBuffer; } // Get Common Controls version information; ulVersionSize = GetFileVersionInfoSize(_T("comctl32.dll"),NULL); if (ulVersionSize > 0) { unsigned char *pBuffer = new unsigned char[ulVersionSize]; if (GetFileVersionInfo(_T("comctl32.dll"),NULL,ulVersionSize,pBuffer)) { if (VerQueryValue(pBuffer,_T("\\"),(void **)&wxFileInfo,(unsigned int *)&ulDummy)) { m_ulMajorCCVersion = wxFileInfo->dwFileVersionMS/65536; m_ulMinorCCVersion = wxFileInfo->dwFileVersionMS%65536; } } delete [] pBuffer; } } CWinVer::~CWinVer() { } #endif ================================================ FILE: src/app/version.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #ifdef VERSION_COMPATIBILITY_CHECK /* Major ----- 4 = Windows NT 4.0, Windows Me, Windows 98, or Windows 95. 5 = Windows Server 2003, Windows XP, or Windows 2000 Minor ----- 0 = Windows 2000, Windows NT 4.0, or Windows 95 1 = Windows XP 2 = Windows Server 2003 10 = Windows 98 90 = Windows Me */ #define MAJOR_WINNT 4 #define MAJOR_WIN95 4 #define MAJOR_WIN98 4 #define MAJOR_WINME 4 #define MAJOR_WIN2000 5 #define MAJOR_WINXP 5 #define MAJOR_WIN2003 5 #define MAJOR_WINVISTA 6 #define MINOR_WINNT4 0 #define MINOR_WIN95 0 #define MINOR_WIN2000 0 #define MINOR_WINVISTA 0 #define MINOR_WINXP 1 #define MINOR_WIN2003 2 #define MINOR_WIN98 10 #define MINOR_WINME 90 class CWinVer { public: // Windows. unsigned long m_ulMajorVersion; unsigned long m_ulMinorVersion; // Internet Explorer. unsigned long m_ulMajorIEVersion; unsigned long m_ulMinorIEVersion; // Common Controls. unsigned long m_ulMajorCCVersion; unsigned long m_ulMinorCCVersion; CWinVer(); ~CWinVer(); }; extern CWinVer g_WinVer; #endif ================================================ FILE: src/app/visual_styles.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "visual_styles.hh" CVisualStyles g_VisualStyles; CVisualStyles::CVisualStyles() { m_hInstance = LoadLibrary(_T("uxtheme.dll")); } CVisualStyles::~CVisualStyles() { if (m_hInstance != NULL) FreeLibrary(m_hInstance); m_hInstance = NULL; } bool CVisualStyles::Supported() { return (m_hInstance != NULL); } bool CVisualStyles::IsThemeActive() { if (!Supported()) return false; PFNISTHEMEACTIVE pfn = (PFNISTHEMEACTIVE)GetProcAddress(m_hInstance,"IsThemeActive"); if (!pfn) return false; return (*pfn)(); } bool CVisualStyles::IsAppThemed() { if (!Supported()) return false; PFNISAPPTHEMED pfnIsAppThemed = (PFNISAPPTHEMED)GetProcAddress(m_hInstance,"IsAppThemed"); if (!pfnIsAppThemed) return false; return (*pfnIsAppThemed)(); } HTHEME CVisualStyles::OpenThemeData(HWND hwnd,LPCWSTR pszClassList) { if (!Supported()) return NULL; PFNOPENTHEMEDATA pfnOpenThemeData = (PFNOPENTHEMEDATA)GetProcAddress(m_hInstance,"OpenThemeData"); if (!pfnOpenThemeData) return NULL; return (*pfnOpenThemeData)(hwnd,pszClassList); } HRESULT CVisualStyles::CloseThemeData(HTHEME hTheme) { if (!Supported()) return false; PFNCLOSETHEMEDATA pfnCloseThemeData = (PFNCLOSETHEMEDATA)GetProcAddress(m_hInstance,"CloseThemeData"); if (!pfnCloseThemeData) return false; return (*pfnCloseThemeData)(hTheme); } HRESULT CVisualStyles::DrawThemeBackground(HTHEME hTheme,HDC hdc, int iPartId,int iStateId,const RECT *pRect,const RECT *pClipRect) { if (!Supported()) return false; PFNDRAWTHEMEBACKGROUND pfnDrawThemeBackground = (PFNDRAWTHEMEBACKGROUND)GetProcAddress(m_hInstance,"DrawThemeBackground"); if (!pfnDrawThemeBackground) return false; return (*pfnDrawThemeBackground)(hTheme,hdc,iPartId,iStateId,pRect,pClipRect); } HRESULT CVisualStyles::GetThemeColor(HTHEME hTheme,int iPartId,int iStateId, int iPropId,COLORREF *pColor) { if (!Supported()) return false; PFNGETTHEMECOLOR pfnGetThemeColor = (PFNGETTHEMECOLOR)GetProcAddress(m_hInstance,"GetThemeColor"); if (!pfnGetThemeColor) return false; return (*pfnGetThemeColor)(hTheme,iPartId,iStateId,iPropId,pColor); } ================================================ FILE: src/app/visual_styles.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include typedef bool (__stdcall *PFNISTHEMEACTIVE)(); typedef bool(__stdcall *PFNISAPPTHEMED)(); typedef HTHEME(__stdcall *PFNOPENTHEMEDATA)(HWND hwnd,LPCWSTR pszClassList); typedef HRESULT(__stdcall *PFNCLOSETHEMEDATA)(HTHEME hTheme); typedef HRESULT(__stdcall *PFNDRAWTHEMEBACKGROUND)(HTHEME hTheme,HDC hdc, int iPartId,int iStateId,const RECT *pRect,const RECT *pClipRect); typedef HRESULT(__stdcall *PFNGETTHEMECOLOR)(HTHEME hTheme,int iPartId, int iStateId,int iPropId,COLORREF *pColor); class CVisualStyles { private: HINSTANCE m_hInstance; bool Supported(); public: CVisualStyles(); ~CVisualStyles(); bool IsThemeActive(); bool IsAppThemed(); HTHEME OpenThemeData(HWND hwnd,LPCWSTR pszClassList); HRESULT CloseThemeData(HTHEME hTheme); HRESULT DrawThemeBackground(HTHEME hTheme,HDC hdc,int iPartId,int iStateId, const RECT *pRect,const RECT *pClipRect); HRESULT GetThemeColor(HTHEME hTheme,int iPartId,int iStateId,int iPropId, COLORREF *pColor); }; extern CVisualStyles g_VisualStyles; ================================================ FILE: src/base/base_vc08.vcproj ================================================ ================================================ FILE: src/base/base_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 base {81EA1BB3-2BA0-4600-9081-2D2CB9203466} base Win32Proj StaticLibrary Unicode true StaticLibrary Unicode StaticLibrary Unicode true StaticLibrary Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) Disabled WIN32;_DEBUG;_WINDOWS;_USRDLL;BASE_EXPORTS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Level3 EditAndContinue X64 Disabled WIN32;_DEBUG;_WINDOWS;_USRDLL;BASE_EXPORTS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Level3 ProgramDatabase WIN32;NDEBUG;_WINDOWS;_USRDLL;BASE_EXPORTS;%(PreprocessorDefinitions) MultiThreaded Level3 ProgramDatabase X64 WIN32;NDEBUG;_WINDOWS;_USRDLL;BASE_EXPORTS;%(PreprocessorDefinitions) MultiThreaded Level3 ProgramDatabase ================================================ FILE: src/base/base_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files ================================================ FILE: src/base/check_fmt_str_placeholders.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include "check_fmt_str_placeholders.hh" // Include file for this module comes first. #include "string_util.hh" #include #define MAX_PARAM_POSITION ((unsigned)100) CFmtStrPlaceholderAnalysis::~CFmtStrPlaceholderAnalysis(void) { for (CVectorOfFmtStrPlaceholder::const_iterator it = m_Placeholders.begin(); it != m_Placeholders.end(); ++it) { const CFmtStrPlaceholder * const pElem = *it; delete pElem; } } void CFmtStrPlaceholderAnalysis::ClearForReuse(void) { // Optimised for reuse: this routine does not free any malloc'ed memory. for (unsigned i = 0; i < m_uPlaceholderCount; ++i) { m_Placeholders[i]->ClearForReuse(); } Init(); } void CFmtStrPlaceholderAnalysis::InsertPlaceholder( const unsigned uPlaceholderPos, // The first position is number 1. const bool bIsPositionalPlaceholder, const ckcore::tchar * const szPlaceholderStr, const unsigned uPlaceholderStrLen) { ATLASSERT(szPlaceholderStr != NULL); ATLASSERT(uPlaceholderStrLen > 0); if (uPlaceholderPos < 1 || uPlaceholderPos > MAX_PARAM_POSITION) throw ckcore::Exception2(ckcore::string::formatstr( _T("Invalid placeholder number %u."),uPlaceholderPos).c_str()); if (m_uPlaceholderCount > 0) { if (m_bPositionalPlaceholders != bIsPositionalPlaceholder) throw ckcore::Exception2(_T("Cannot mix positional and non-positional placeholders.")); } m_bPositionalPlaceholders = bIsPositionalPlaceholder; m_uPlaceholderCount = (std::max)(m_uPlaceholderCount,uPlaceholderPos); if (m_Placeholders.size() < m_uPlaceholderCount) m_Placeholders.resize(m_uPlaceholderCount); if (m_Placeholders[uPlaceholderPos - 1] == NULL) m_Placeholders[uPlaceholderPos - 1] = new CFmtStrPlaceholder; CFmtStrPlaceholder * const plh = m_Placeholders[uPlaceholderPos - 1]; // According to the format string specification, you can reference the same // argument from several placeholders, an each placeholder can have // different format specifiers. However, we don't allow it here, because of // the extra complication that would add to this testing class. Fortunately, // this feature is rarely used. if (!plh->m_Placeholder.empty()) throw ckcore::Exception2(ckcore::string::formatstr(_T("Placeholder %u already used."),uPlaceholderPos).c_str()); plh->m_Placeholder.insert(plh->m_Placeholder.begin(), szPlaceholderStr,szPlaceholderStr + uPlaceholderStrLen); } // ---------------------------------------------------------------------------- // WARNING: This format string parser is not complete, and will not process all // possible cases and find all possible errors. Writing a full parser // which could also accomodate cross-platform differences is not a // trivial task.I have made however a reasonably effort to error on // all unsupported cases. // ---------------------------------------------------------------------------- // Advances p as necessary. static bool IsPlaceholderLength(const ckcore::tchar ** const p) { // According to the Microsoft documentation, these are the possible // indicators for field [length] inside a format string: // {h | l | ll | I | I32 | I64} switch (**p) { case _T('h'): ++*p; return true; case _T('l'): ++*p; if (**p == 'l') ++*p; return true; case _T('I'): { ++*p; const ckcore::tchar *t = *p; if (*t == _T('3')) { ++t; if (*t == _T('2')) { ++t; *p = t; return true; } } else if (*t == _T('6')) { ++t; if (*t == _T('4')) { ++t; *p = t; return true; } } return true; // An 'I' alone. } default: return false; } } static bool IsPlaceholderType(const ckcore::tchar c) { switch (c) { case _T('d'): case _T('i'): case _T('u'): case _T('f'): case _T('F'): case _T('e'): case _T('E'): case _T('g'): case _T('G'): case _T('x'): case _T('X'): case _T('o'): case _T('s'): case _T('c'): case _T('p'): case _T('n'): return true; default: return false; } } static bool IsPlaceholderFlag(const ckcore::tchar c) { switch ( c ) { case _T('-'): case _T('+'): case _T('0'): case _T(' '): case _T('#'): return true; default: return false; } } static bool ReadPositionalParam(const ckcore::tchar ** const p,unsigned * const uPlaceholderPos) { // Skip any digits at the current position, and look at the next character; // If it's a dollar ($) symbol, then this was a positional parameter. // If not, it may be the [width] field or something else. const ckcore::tchar *scan = *p; if (*scan < _T('0') || *scan > _T('9')) return false; unsigned uVal = 0; do { // If the value of MAX_PARAM_POSITION changes, make sure that it' still // ten times lower than the maximum integer value. Otherwise, we need // to explicitly test here against integer overflow when multiplying. ATLASSERT(MAX_PARAM_POSITION <= 1000); uVal *= 10; uVal += *scan - _T('0'); if (uVal > MAX_PARAM_POSITION) throw ckcore::Exception2(_T("Integer too big parsing the positional parameter.")); ++scan; } while (*scan >= _T('0') && *scan <= _T('9')); if (*scan != _T('$')) return false; *uPlaceholderPos = uVal; *p = scan + 1; return true; } void CFmtStrPlaceholderAnalysis::AnalyzeFormatString(const ckcore::tchar * const szFmtStr) { // The analysis results should be empty upon entry. ATLASSERT(m_uPlaceholderCount == 0); // printf format string format // // %[parameter] [flags] [width] [.precision] [length] type // // [parameter] is an optional positional argument specifier like "1$". // That means, old-style "%s" would look like "%1$s" for the first // positional argument. unsigned uPlaceholderPos = 1; for (const ckcore::tchar * p = szFmtStr; *p != _T('\0');) { if (*p != _T('%')) { ++p; continue; } const ckcore::tchar * const placeholderStart = p; ++p; if (*p == _T('%')) { ++p; continue; } try { if (*p == _T('\0')) throw ckcore::Exception2(_T("Invalid placeholder at the end of the string.")); const bool bIsPositionalParam = ReadPositionalParam(&p,&uPlaceholderPos); while (IsPlaceholderFlag(*p)) ++p; // Skip the optional width. while (*p >= _T('1') && *p <= _T('9')) ++p; // Skip the optional precision. if (*p == _T('.')) { ++p; while (*p >= _T('0') && *p <= _T('9')) ++p; } // Skip the optional length. IsPlaceholderLength(&p); if (IsPlaceholderType(*p)) { ++p; InsertPlaceholder(uPlaceholderPos, bIsPositionalParam, placeholderStart, p - placeholderStart); ++uPlaceholderPos; continue; } throw ckcore::Exception2(_T("Invalid or unsupported placeholder.")); } catch (const std::exception &e) { ckcore::rethrow_with_pfx(e,_T("Error at line position %d: "), placeholderStart - szFmtStr + 1); } } // Check here that there are no empty placeholders. // // Microsoft's implementation of _printf_p does generate a run-time error // if any of the parameters are left unreferenced. This can only be detected // if the unreferenced parameter is in the middle of other parameters. // For example, for a format string like "%1$s %3$s", the run-time library // complains that parameter 2 is not used. for (unsigned i = 0; i < m_uPlaceholderCount; ++i) { if (m_Placeholders[i] == NULL || m_Placeholders[i]->m_Placeholder.empty()) throw ckcore::Exception2(ckcore::string::formatstr(_T("Positional argument %u not referenced in the format string."),i + 1).c_str()); } } void CFmtStrPlaceholderAnalysis::ComparePlaceholderAnalyses(const CFmtStrPlaceholderAnalysis * const pAnalysis1, const CFmtStrPlaceholderAnalysis * const pAnalysis2) { // NOTE: This method is static. if (pAnalysis1->m_uPlaceholderCount != pAnalysis2->m_uPlaceholderCount) { throw ckcore::Exception2(_T("The strings being compared do not contain the same number of placeholders.")); } if (pAnalysis1->m_uPlaceholderCount > 0 && pAnalysis1->m_bPositionalPlaceholders != pAnalysis2->m_bPositionalPlaceholders) { throw ckcore::Exception2(_T("The strings being compared are not using the same type of placeholders (positional vs non-positional).")); } for (unsigned int i = 0; i < pAnalysis1->m_uPlaceholderCount; ++i) { const CFmtStrPlaceholder * const plh1 = pAnalysis1->m_Placeholders[i]; const CFmtStrPlaceholder * const plh2 = pAnalysis2->m_Placeholders[i]; if (plh1->m_Placeholder != plh2->m_Placeholder) { throw ckcore::Exception2( ckcore::string::formatstr(_T("Placeholder number %u in the second string (\"%s\") differs from the corresponding one in the first string (\"%s\")."), i + 1, plh2->m_Placeholder.c_str(), plh1->m_Placeholder.c_str()).c_str()); } } } void ComparePlaceholdersInTranslatedStr(const ckcore::tchar * const szSectionName, const unsigned uStringId, const ckcore::tchar * const szReferencedFmtStr, const ckcore::tchar * const szTranslatedFmtStr, CFmtStrPlaceholderAnalysis * const pAnalysis1, // Reused for performance CFmtStrPlaceholderAnalysis * const pAnalysis2) // Reused for performance { pAnalysis1->ClearForReuse(); pAnalysis2->ClearForReuse(); try { try { pAnalysis1->AnalyzeFormatString(szReferencedFmtStr); } catch (const std::exception &e) { ckcore::rethrow_with_pfx(e,_T("Error parsing the reference string: ")); } try { pAnalysis2->AnalyzeFormatString(szTranslatedFmtStr); } catch ( const std::exception &e) { ckcore::rethrow_with_pfx(e,_T("Error parsing the translated string: ")); } CFmtStrPlaceholderAnalysis::ComparePlaceholderAnalyses(pAnalysis1,pAnalysis2); } catch (const std::exception &e) { ckcore::rethrow_with_pfx(e,_T("Error in section [%s], string ID 0x%X: "), szSectionName,uStringId); } } ================================================ FILE: src/base/check_fmt_str_placeholders.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include class CFmtStrPlaceholder { public: // In the future, we will probably have here more data about this placeholder. ckcore::tstring m_Placeholder; // Examples: "%s", "%1$s", "%3d". void ClearForReuse(void) { m_Placeholder.clear(); } }; typedef std::vector CVectorOfFmtStrPlaceholder; class CFmtStrPlaceholderAnalysis { public: CFmtStrPlaceholderAnalysis(void) { Init(); } ~CFmtStrPlaceholderAnalysis(void); void AnalyzeFormatString(const ckcore::tchar *szFmtStr); static void ComparePlaceholderAnalyses(const CFmtStrPlaceholderAnalysis *pAnalysis1, const CFmtStrPlaceholderAnalysis *pAnalysis2); void ClearForReuse(void); protected: unsigned m_uPlaceholderCount; // Always <= m_placeholders.size(). Note that, when reusing an object, // m_placeholders.size() could be bigger. CVectorOfFmtStrPlaceholder m_Placeholders; bool m_bPositionalPlaceholders; // Like "%1$s", as opposed to "%s". void Init(void) { m_uPlaceholderCount = 0; m_bPositionalPlaceholders = false; } void InsertPlaceholder(unsigned uPlaceholderPos, bool bIsPositionalPlaceholder, const ckcore::tchar *szPlaceholderStr, unsigned uPlaceholderStrLen); }; void ComparePlaceholdersInTranslatedStr(const ckcore::tchar *szSectionName, unsigned uStringId, const ckcore::tchar *szReferencedFmtStr, const ckcore::tchar *szTranslatedFmtStr, CFmtStrPlaceholderAnalysis *pAnalysis1, CFmtStrPlaceholderAnalysis *pAnalysis2); ================================================ FILE: src/base/codec_const.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include // Callback function definitions. #define IRC_MESSAGE_INFO 0 #define IRC_MESSAGE_WARNING 1 #define IRC_MESSAGE_ERROR 2 typedef void CALLBACK tirc_send_message(int iType,const TCHAR *szMessage); // Exported codec function types. typedef int (WINAPI *tirc_capabilities)(); typedef TCHAR *(WINAPI *tirc_string)(unsigned int uiID); typedef bool (WINAPI *tirc_set_callback)(tirc_send_message *pSendMessage); typedef bool (WINAPI *tirc_decode_init)(const TCHAR *szFileName,int &iNumChannels,int &iSampleRate,int &iBitRate,unsigned __int64 &uiDuration); typedef __int64 (WINAPI *tirc_decode_process)(unsigned char *pBuffer,__int64 iBufferSize,unsigned __int64 &uiTime); typedef bool (WINAPI *tirc_decode_exit)(); typedef bool (WINAPI *tirc_encode_init)(const TCHAR *szFileName,int iNumChannels,int iSampleRate,int iBitRate); typedef __int64 (WINAPI *tirc_encode_process)(unsigned char *pBuffer,__int64 iDataSize); typedef __int64 (WINAPI *tirc_encode_flush)(); typedef bool (WINAPI *tirc_encode_exit)(); typedef bool (WINAPI *tirc_encode_config)(); // Capability flags. #define IRC_HAS_DECODER 0x0001 #define IRC_HAS_ENCODER 0x0002 #define IRC_HAS_CONFIG 0x0004 // String identifiers. #define IRC_STR_VERSION 0 #define IRC_STR_ABOUT 1 #define IRC_STR_ENCODER 2 #define IRC_STR_FILEEXT 3 ================================================ FILE: src/base/codec_manager.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include "codec_manager.hh" CCodec::CCodec() { m_hInstance = NULL; } CCodec::~CCodec() { if (m_hInstance) FreeLibrary(m_hInstance); } bool CCodec::Load(const TCHAR *szFileName) { m_hInstance = LoadLibrary(szFileName); if (m_hInstance == NULL) return false; irc_capabilities = (tirc_capabilities)GetProcAddress(m_hInstance,"irc_capabilities"); if (!irc_capabilities) return false; irc_string = (tirc_string)GetProcAddress(m_hInstance,"irc_string"); if (!irc_string) return false; irc_set_callback = (tirc_set_callback)GetProcAddress(m_hInstance,"irc_set_callback"); if (!irc_set_callback) return false; irc_decode_init = (tirc_decode_init)GetProcAddress(m_hInstance,"irc_decode_init"); if (!irc_decode_init) return false; irc_decode_process = (tirc_decode_process)GetProcAddress(m_hInstance,"irc_decode_process"); if (!irc_decode_process) return false; irc_decode_exit = (tirc_decode_exit)GetProcAddress(m_hInstance,"irc_decode_exit"); if (!irc_decode_exit) return false; irc_encode_init = (tirc_encode_init)GetProcAddress(m_hInstance,"irc_encode_init"); if (!irc_encode_init) return false; irc_encode_process = (tirc_encode_process)GetProcAddress(m_hInstance,"irc_encode_process"); if (!irc_encode_process) return false; irc_encode_flush = (tirc_encode_flush)GetProcAddress(m_hInstance,"irc_encode_flush"); if (!irc_encode_flush) return false; irc_encode_exit = (tirc_encode_exit)GetProcAddress(m_hInstance,"irc_encode_exit"); if (!irc_encode_exit) return false; irc_encode_config = (tirc_encode_config)GetProcAddress(m_hInstance,"irc_encode_config"); if (!irc_encode_config) return false; return true; } bool CCodec::GetFileName(TCHAR *szFileName,unsigned long ulBufSize) { return ::GetModuleFileName(m_hInstance,szFileName,ulBufSize) != 0; } CCodecManager::CCodecManager() { m_bIsLoaded = false; } CCodecManager::~CCodecManager() { for (unsigned int iIndex = 0; iIndex < m_Codecs.size(); iIndex++) { // Remove the object from m_Instances. std::vector ::iterator itObject = m_Codecs.begin() + iIndex; delete *itObject; } m_Codecs.clear(); } bool CCodecManager::LoadCodec(const TCHAR *szFileName) { CCodec *pCodec = new CCodec(); if (!pCodec->Load(szFileName)) { delete pCodec; return false; } m_Codecs.push_back(pCodec); return true; } bool CCodecManager::LoadCodecs(const TCHAR *szCodecPath) { ckcore::Path CodecPath = szCodecPath; ckcore::Directory CodecDir(CodecPath); ckcore::Directory::Iterator itDir; for (itDir = CodecDir.begin(); itDir != CodecDir.end(); itDir++) { ckcore::Path PluginPath = CodecPath + (*itDir).c_str(); if (!lstrcmpi(PluginPath.ext_name().c_str(),ckT("irc"))) { if (!LoadCodec(PluginPath.name().c_str())) return false; } } m_bIsLoaded = true; return true; } bool CCodecManager::IsLoaded() { return m_bIsLoaded; } ================================================ FILE: src/base/codec_manager.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "codec_const.hh" // Local structures. class CCodec { private: HINSTANCE m_hInstance; public: CCodec(); ~CCodec(); bool Load(const TCHAR *szFileName); bool GetFileName(TCHAR *szFileName,unsigned long ulBufSize); tirc_capabilities irc_capabilities; tirc_string irc_string; tirc_set_callback irc_set_callback; tirc_decode_init irc_decode_init; tirc_decode_process irc_decode_process; tirc_decode_exit irc_decode_exit; tirc_encode_init irc_encode_init; tirc_encode_process irc_encode_process; tirc_encode_flush irc_encode_flush; tirc_encode_exit irc_encode_exit; tirc_encode_config irc_encode_config; }; class CCodecManager { private: bool m_bIsLoaded; bool LoadCodec(const TCHAR *szFileName); public: CCodecManager(); ~CCodecManager(); std::vector m_Codecs; bool LoadCodecs(const TCHAR *szCodecPath); bool IsLoaded(); }; ================================================ FILE: src/base/custom_string.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "string_util.hh" #define CSTRING_DEFAULT_LENGTH 256 #define CSTRING_MEM_INCRATIO 2 class CCustomString { private: TCHAR *m_szString; unsigned int m_uiSize; unsigned int m_uiPos; public: CCustomString() { m_uiSize = CSTRING_DEFAULT_LENGTH; m_uiPos = 0; m_szString = new TCHAR[m_uiSize]; } CCustomString(unsigned int uiSize) { m_uiSize = uiSize; m_uiPos = 0; m_szString = new TCHAR[m_uiSize]; } ~CCustomString() { delete [] m_szString; } void Reset() { m_uiPos = 0; } void ReAllocate(unsigned int uiSize) { m_uiSize = uiSize; m_uiPos = 0; delete [] m_szString; m_szString = new TCHAR[m_uiSize]; } void Append(TCHAR c) { if (m_uiPos >= m_uiSize) { m_uiSize *= CSTRING_MEM_INCRATIO; TCHAR *szNewString = new TCHAR[m_uiSize]; lstrncpy(szNewString,m_szString,m_uiSize / CSTRING_MEM_INCRATIO); delete [] m_szString; m_szString = szNewString; } m_szString[m_uiPos++] = c; } void AppendString(const TCHAR *szString) { size_t iStrLen = lstrlen(szString); for (size_t i = 0; i < iStrLen; i++) Append(szString[i]); } void CopyFromHtml(const TCHAR *szNewString) { size_t iNewStrLen = lstrlen(szNewString); Reset(); for (size_t i = 0; i < iNewStrLen; i++) { if (szNewString[i] == '&') AppendString(_T("&")); else if (szNewString[i] == '"') AppendString(_T(""")); else if (szNewString[i] == '<') AppendString(_T("<")); else if (szNewString[i] == '>') AppendString(_T(">")); else Append(szNewString[i]); } Append('\0'); } void CopyFrom(const TCHAR *szNewString) { lstrcpy(m_szString,szNewString); m_uiPos = lstrlen(szNewString); } unsigned int Length() { return m_uiPos; } operator TCHAR *() { return m_szString; } }; class CCustomStringA { private: char *m_szString; unsigned int m_uiSize; unsigned int m_uiPos; public: CCustomStringA() { m_uiSize = CSTRING_DEFAULT_LENGTH; m_uiPos = 0; m_szString = new char[m_uiSize]; } CCustomStringA(unsigned int uiSize) { m_uiSize = uiSize; m_uiPos = 0; m_szString = new char[m_uiSize]; } ~CCustomStringA() { delete [] m_szString; } void Reset() { m_uiPos = 0; } void ReAllocate(unsigned int uiSize) { m_uiSize = uiSize; m_uiPos = 0; delete [] m_szString; m_szString = new char[m_uiSize]; } void Append(char c) { if (m_uiPos >= m_uiSize) { m_uiSize *= CSTRING_MEM_INCRATIO; char *szNewString = new char[m_uiSize]; strcpy(szNewString,m_szString); delete [] m_szString; m_szString = szNewString; } m_szString[m_uiPos++] = c; } void CopyFrom(const char *szNewString) { strcpy(m_szString,szNewString); m_uiPos = (unsigned int)strlen(szNewString); } unsigned int Length() { return m_uiPos; } operator char *() { return m_szString; } }; ================================================ FILE: src/base/file_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include #include "file_util.hh" void WriteString(ckcore::File &File,const ckcore::tchar *szString) { const ckcore::tuint32 uiByteCount = static_cast(ckcore::string::astrlen(szString) * sizeof(ckcore::tchar)); if (uiByteCount != File.write(szString,uiByteCount)) throw ckcore::Exception2(ckT("Error writing to the file.")); // FIXME: Improve message output. } ================================================ FILE: src/base/file_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include void WriteString(ckcore::File &File,const ckcore::tchar *szString); ================================================ FILE: src/base/graph_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include "graph_util.hh" void DrawVertGradientRect(HDC hDC,RECT *pRect,COLORREF cTop,COLORREF cBottom) { unsigned int uiClientHeight = pRect->bottom - pRect->top; RECT rcBand; rcBand.left = pRect->left; rcBand.right = pRect->right; int iBeginRGB[3]; int iRGBDiff[3]; int iR,iG,iB; iBeginRGB[0] = GetRValue(cTop); iBeginRGB[1] = GetGValue(cTop); iBeginRGB[2] = GetBValue(cTop); iRGBDiff[0] = GetRValue(cBottom) - iBeginRGB[0]; iRGBDiff[1] = GetGValue(cBottom) - iBeginRGB[1]; iRGBDiff[2] = GetBValue(cBottom) - iBeginRGB[2]; for (int i = pRect->top,j = 0; i < pRect->bottom; i++,j++) { iR = iBeginRGB[0] + MulDiv(j,iRGBDiff[0],uiClientHeight); iG = iBeginRGB[1] + MulDiv(j,iRGBDiff[1],uiClientHeight); iB = iBeginRGB[2] + MulDiv(j,iRGBDiff[2],uiClientHeight); rcBand.top = (int)(i); rcBand.bottom = (int)((i + 1)); HBRUSH hBrush = CreateSolidBrush(RGB(iR,iG,iB)); FillRect(hDC,&rcBand,hBrush); DeleteObject(hBrush); } } void DrawHorGradientRect(HDC hDC,RECT *pRect,COLORREF cLeft,COLORREF cRight) { unsigned int uiClientWidth = pRect->right - pRect->left; RECT rcBand; rcBand.top = pRect->top; rcBand.bottom = pRect->bottom; int iBeginRGB[3]; int iRGBDiff[3]; int iR,iG,iB; iBeginRGB[0] = GetRValue(cLeft); iBeginRGB[1] = GetGValue(cLeft); iBeginRGB[2] = GetBValue(cLeft); iRGBDiff[0] = GetRValue(cRight) - iBeginRGB[0]; iRGBDiff[1] = GetGValue(cRight) - iBeginRGB[1]; iRGBDiff[2] = GetBValue(cRight) - iBeginRGB[2]; for (int i = pRect->left,j = 0; i < pRect->right; i++,j++) { iR = iBeginRGB[0] + MulDiv(j,iRGBDiff[0],uiClientWidth); iG = iBeginRGB[1] + MulDiv(j,iRGBDiff[1],uiClientWidth); iB = iBeginRGB[2] + MulDiv(j,iRGBDiff[2],uiClientWidth); rcBand.left = (int)(i); rcBand.right = (int)((i + 1)); HBRUSH hBrush = CreateSolidBrush(RGB(iR,iG,iB)); FillRect(hDC,&rcBand,hBrush); DeleteObject(hBrush); } } void ContractRect(RECT *pRect,int iSize) { pRect->left += iSize; pRect->right -= iSize; pRect->top += iSize; pRect->bottom -= iSize; } ================================================ FILE: src/base/graph_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once void DrawVertGradientRect(HDC hDC,RECT *pRect,COLORREF cTop,COLORREF cBottom); void DrawHorGradientRect(HDC hDC,RECT *pRect,COLORREF cLeft,COLORREF cRight); void ContractRect(RECT *pRect,int iSize); ================================================ FILE: src/base/lng_processor.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include "lng_processor.hh" #include "string_conv.hh" #include "string_util.hh" CLngProcessor::CLngProcessor(const TCHAR *szFullPath) : m_File(szFullPath) { m_ulBufferSize = 0; m_ulBufferPos = 0; memset(m_ucBuffer,0,sizeof(m_ucBuffer)); // Set the current child to the root. m_pCurrent = NULL; } CLngProcessor::~CLngProcessor() { Clear(); } void CLngProcessor::Clear() { // Free the children. for (unsigned int iIndex = 0; iIndex < m_pSections.size(); iIndex++) { // Remove the object from m_Instances. std::vector ::iterator itObject = m_pSections.begin() + iIndex; delete *itObject; } m_pSections.clear(); } bool CLngProcessor::ReadNext(TCHAR &c) { if (m_ulBufferPos == m_ulBufferSize) { memset(m_ucBuffer,0,sizeof(m_ucBuffer)); ckcore::tint64 iRead = m_File.read(m_ucBuffer,sizeof(m_ucBuffer)); if (iRead == -1) return false; m_ulBufferSize = (unsigned long)iRead; m_ulBufferSize /= sizeof(TCHAR); m_ulBufferPos = 0; TCHAR sz; sz = true; if (m_ulBufferSize == 0) return false; } m_iRemainBytes -= sizeof(TCHAR); c = m_ucBuffer[m_ulBufferPos++]; return true; } void CLngProcessor::ReadBack() { if (m_ulBufferPos > 0) { m_iRemainBytes += sizeof(TCHAR); m_ulBufferPos--; } } /* CLngProcessor::Load ------------------- Loads the specified XML into a tree structure in memory. Varius return values. */ int CLngProcessor::Load() { // Open the file. if (!m_File.open(ckcore::File::ckOPEN_READ)) return LNGRES_FILEERROR; // If the application is in an unicode environment we need to check what // byte-order us used. unsigned short usBOM = 0; if (m_File.read(&usBOM,2) == -1) return LNGRES_FILEERROR; switch (usBOM) { // Currently the only supported byte-order. case BOM_UTF32BE: break; case BOM_UTF8: case BOM_UTF32LE: case BOM_SCSU: return LNGRES_UNSUPBOM; default: // If no BOM is found the file pointer has to be re-moved to the beginning. if (m_File.seek(0,ckcore::File::ckFILE_BEGIN) == -1) return LNGRES_FILEERROR; break; }; // Clear all current sections. Clear(); // Set the current section to NULL. m_pCurrent = NULL; // The current section (when parsing). CLngSection *pCurSection = NULL; CCustomString szNameBuffer(11); m_iRemainBytes = m_File.size() - m_File.tell(); bool bBreak = false; int iCount = 0; while (m_iRemainBytes) { iCount++; TCHAR uc; if (!ReadNext(uc)) break; // Trim. while (uc == ' ' || uc == '\t' || uc == '\r' || uc == '\n') { if (!ReadNext(uc)) { bBreak = true; break; } } if (bBreak) break; // We have found the beginning of a section. if (uc == '[') { if (!ReadNext(uc)) break; pCurSection = new CLngSection(); m_pSections.push_back(pCurSection); while (uc != ']') { pCurSection->m_szName.Append(uc); if (!ReadNext(uc)) break; } pCurSection->m_szName.Append('\0'); } else { // Ignore all values that are not associated with a section. if (pCurSection == NULL) continue; // If we didn't find a section we have found a value. CLngValue *pNewValue = new CLngValue(); while (uc != '=') { szNameBuffer.Append(uc); if (!ReadNext(uc)) break; } szNameBuffer.Append('\0'); lsscanf(szNameBuffer,_T("%x"),&pNewValue->ulName); szNameBuffer.Reset(); // Skip the '='. if (!ReadNext(uc)) break; while (uc != '\n' && uc != '\r') { // Look for esacpe. if (uc == '\\') { TCHAR uc0 = '\0'; if (!ReadNext(uc0)) { szNameBuffer.Append(uc); break; } if (uc0 == '\n' || uc0 == '\r') break; switch (uc0) { case 'n': pNewValue->m_szValue.Append('\n'); break; default: pNewValue->m_szValue.Append(uc); pNewValue->m_szValue.Append(uc0); break; } } else { pNewValue->m_szValue.Append(uc); } if (!ReadNext(uc)) break; } pNewValue->m_szValue.Append('\0'); pCurSection->m_Values.push_back(pNewValue); } } return LNGRES_OK; } bool CLngProcessor::EnterSection(const TCHAR *szSectionName) { // First, check if we're already in the requested section. if (m_pCurrent != NULL && !lstrcmp(szSectionName,m_pCurrent->m_szName)) return true; for (unsigned int i = 0; i < m_pSections.size(); i++) { if (!lstrcmp(szSectionName,m_pSections[i]->m_szName)) { m_pCurrent = m_pSections[i]; return true; } } return false; } bool CLngProcessor::GetValue(unsigned long ulName,TCHAR *szValue,unsigned int uiMaxValueLen) { if (m_pCurrent == NULL) return false; for (unsigned int i = 0; i < m_pCurrent->m_Values.size(); i++) { if (m_pCurrent->m_Values[i]->ulName == ulName) { if ((unsigned int)lstrlen(m_pCurrent->m_Values[i]->m_szValue) > uiMaxValueLen) lstrncpy(szValue,m_pCurrent->m_Values[i]->m_szValue,uiMaxValueLen); else lstrcpy(szValue,m_pCurrent->m_Values[i]->m_szValue); return true; } } return false; } bool CLngProcessor::GetValuePtr(unsigned long ulName,TCHAR *&szValue) { if (m_pCurrent == NULL) return false; for (unsigned int i = 0; i < m_pCurrent->m_Values.size(); i++) { if (m_pCurrent->m_Values[i]->ulName == ulName) { szValue = m_pCurrent->m_Values[i]->m_szValue; return true; } } return false; } ================================================ FILE: src/base/lng_processor.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include "custom_string.hh" #define BOM_UTF8 0xEFBBBF #define BOM_UTF32BE 0x0000FEFF #define BOM_UTF32LE 0xFFFE0000 #define BOM_SCSU 0x0EFEFF #define LNG_NAMELENGTH 128 #define LNG_VALUELENGTH 128 #define LNG_BUFFER_SIZE 1024 // Return values. #define LNGRES_FAIL 0x00 #define LNGRES_OK 0x01 #define LNGRES_FILEERROR 0x02 #define LNGRES_UNSUPBOM 0x03 class CLngValue { public: unsigned long ulName; CCustomString m_szValue; CLngValue() : m_szValue(LNG_VALUELENGTH) { ulName = 0; m_szValue[0] = '\0'; } CLngValue(unsigned int uiValueLength) : m_szValue(uiValueLength) { ulName = 0; m_szValue[0] = '\0'; } }; class CLngSection { public: CCustomString m_szName; std::vector m_Values; CLngSection() : m_szName(LNG_NAMELENGTH) { m_szName[0] = '\0'; } CLngSection(unsigned int uiNameLength) : m_szName(uiNameLength) { m_szName[0] = '\0'; } ~CLngSection() { Clear(); } void Clear() { // Free the children. for (unsigned int iIndex = 0; iIndex < m_Values.size(); iIndex++) { // Remove the object from m_Instances. std::vector ::iterator itObject = m_Values.begin() + iIndex; delete *itObject; } m_Values.clear(); } }; class CLngProcessor { protected: ckcore::File m_File; TCHAR m_ucBuffer[LNG_BUFFER_SIZE]; unsigned long m_ulBufferSize; unsigned long m_ulBufferPos; __int64 m_iRemainBytes; std::vector m_pSections; CLngSection *m_pCurrent; void Clear(); bool ReadNext(TCHAR &c); void ReadBack(); public: CLngProcessor(const TCHAR *szFullPath); ~CLngProcessor(); int Load(); bool EnterSection(const TCHAR *szSectionName); bool GetValue(unsigned long ulName,TCHAR *szValue,unsigned int uiMaxValueLen); bool GetValuePtr(unsigned long ulName,TCHAR *&szValue); }; ================================================ FILE: src/base/string_container.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include "string_container.hh" #include "custom_string.hh" CStringContainer::CStringContainer() { m_ulBufferSize = 0; m_ulBufferPos = 0; memset(m_ucBuffer,0,sizeof(m_ucBuffer)); } CStringContainer::~CStringContainer() { m_szStrings.clear(); } bool CStringContainer::ReadNext(ckcore::File &File,TCHAR &c) { if (m_ulBufferPos == m_ulBufferSize) { memset(m_ucBuffer,0,sizeof(m_ucBuffer)); ckcore::tint64 iRead = File.read(m_ucBuffer,sizeof(m_ucBuffer)); if (iRead == -1) return false; m_ulBufferSize = (unsigned long)iRead; m_ulBufferSize /= sizeof(TCHAR); m_ulBufferPos = 0; if (m_ulBufferSize == 0) return false; } m_iRemainBytes -= sizeof(TCHAR); c = m_ucBuffer[m_ulBufferPos++]; return true; } /* CStringContainer::SaveToFile ---------------------------- Saves the container data to the file with the specified file name. If bCRLF is set each line will be terminated with , otherwise only a new line (Line-Feed) will be used. */ int CStringContainer::SaveToFile(const TCHAR *szFileName,bool bCRLF) { ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_WRITE)) return SCRES_FAIL; // Write byte order mark. unsigned short usBOM = BOM_UTF32BE; if (File.write(&usBOM,2) == -1) return SCRES_FAIL; // Find the longest string. unsigned int uiLongestString = 0; for (unsigned int i = 0; i < m_szStrings.size(); i++) { if (m_szStrings[i].length() > uiLongestString) uiLongestString = (unsigned int)m_szStrings[i].length(); } // Write the strings to the file. TCHAR *szBuffer = new TCHAR[uiLongestString + 3]; for (unsigned int i = 0; i < m_szStrings.size(); i++) { lstrcpy(szBuffer,m_szStrings[i].c_str()); if (bCRLF) lstrcat(szBuffer,TEXT("\r\n")); else lstrcat(szBuffer,TEXT("\n")); if (File.write((void *)szBuffer,lstrlen(szBuffer) * sizeof(TCHAR)) == -1) { delete [] szBuffer; return SCRES_FAIL; } } delete [] szBuffer; return SCRES_OK; } int CStringContainer::LoadFromFile(const TCHAR *szFileName) { ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_READ)) return SCRES_FAIL; // Read byte order mark. unsigned short usBOM = 0; if (File.read(&usBOM,2) == -1) return SCRES_FAIL; switch (usBOM) { // Currently the only supported byte-order. case BOM_UTF32BE: break; case BOM_UTF8: case BOM_UTF32LE: case BOM_SCSU: return SCRES_UNSUPBOM; default: // If no BOM is found the file pointer has to be re-moved to the beginning. if (File.seek(0,ckcore::File::ckFILE_BEGIN) == -1) return SCRES_FAIL; break; }; // Read the file data. CCustomString Buffer(256); m_iRemainBytes = File.size(); while (m_iRemainBytes) { TCHAR uc; if (!ReadNext(File,uc)) break; if (uc == '\r') { continue; } else if (uc == '\n') { Buffer.Append('\0'); m_szStrings.push_back((TCHAR *)Buffer); Buffer.Reset(); continue; } Buffer.Append(uc); } return SCRES_OK; } CStringContainerA::CStringContainerA() { m_ulBufferSize = 0; m_ulBufferPos = 0; memset(m_ucBuffer,0,sizeof(m_ucBuffer)); } CStringContainerA::~CStringContainerA() { m_szStrings.clear(); } bool CStringContainerA::ReadNext(ckcore::File &File,char &c) { if (m_ulBufferPos == m_ulBufferSize) { memset(m_ucBuffer,0,sizeof(m_ucBuffer)); ckcore::tint64 iRead = File.read(m_ucBuffer,sizeof(m_ucBuffer)); if (iRead == -1) return false; m_ulBufferSize = (unsigned long)iRead; m_ulBufferPos = 0; if (m_ulBufferSize == 0) return false; } m_iRemainBytes--; c = m_ucBuffer[m_ulBufferPos++]; return true; } /* CStringContainer::SaveToFile ---------------------------- Saves the container data to the file with the specified file name. If bCRLF is set each line will be terminated with , otherwise only a new line (Line-Feed) will be used. */ int CStringContainerA::SaveToFile(const TCHAR *szFileName,bool bCRLF) { ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_WRITE)) return SCRES_FAIL; // Find the longest string. unsigned int uiLongestString = 0; for (unsigned int i = 0; i < m_szStrings.size(); i++) { if (m_szStrings[i].length() > uiLongestString) uiLongestString = (unsigned int)m_szStrings[i].length(); } // Write the strings to the file. char *szBuffer = new char[uiLongestString + 3]; for (unsigned int i = 0; i < m_szStrings.size(); i++) { strcpy(szBuffer,m_szStrings[i].c_str()); if (bCRLF) strcat(szBuffer,"\r\n"); else strcat(szBuffer,"\n"); if (File.write((void *)szBuffer,(unsigned long)strlen(szBuffer)) == -1) { delete [] szBuffer; return SCRES_FAIL; } } delete [] szBuffer; return SCRES_OK; } int CStringContainerA::LoadFromFile(const TCHAR *szFileName) { ckcore::File File(szFileName); if (!File.open(ckcore::File::ckOPEN_READ)) return SCRES_FAIL; // Read the file data. CCustomStringA Buffer(256); m_iRemainBytes = File.size(); while (m_iRemainBytes) { char uc; if (!ReadNext(File,uc)) break; if (uc == '\r') { continue; } else if (uc == '\n') { Buffer.Append('\0'); m_szStrings.push_back((char *)Buffer); Buffer.Reset(); continue; } Buffer.Append(uc); } return SCRES_OK; } ================================================ FILE: src/base/string_container.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #define BOM_UTF8 0xEFBBBF #define BOM_UTF32BE 0x0000FEFF #define BOM_UTF32LE 0xFFFE0000 #define BOM_SCSU 0x0EFEFF #define SCRES_FAIL 0x00 #define SCRES_OK 0x01 #define SCRES_UNSUPBOM 0x02 #define SC_BUFFER_SIZE 1024 class CStringContainer { private: TCHAR m_ucBuffer[SC_BUFFER_SIZE]; unsigned long m_ulBufferSize; unsigned long m_ulBufferPos; __int64 m_iRemainBytes; bool ReadNext(ckcore::File &File,TCHAR &c); public: std::vector m_szStrings; CStringContainer(); ~CStringContainer(); int SaveToFile(const TCHAR *szFileName,bool bCRLF = true); int LoadFromFile(const TCHAR *szFileName); }; class CStringContainerA { private: char m_ucBuffer[SC_BUFFER_SIZE]; unsigned long m_ulBufferSize; unsigned long m_ulBufferPos; __int64 m_iRemainBytes; bool ReadNext(ckcore::File &File,char &c); public: std::vector m_szStrings; CStringContainerA(); ~CStringContainerA(); int SaveToFile(const TCHAR *szFileName,bool bCRLF = true); int LoadFromFile(const TCHAR *szFileName); }; ================================================ FILE: src/base/string_conv.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include "string_conv.hh" int StringToInt(const TCHAR *szString) { return _wtoi(szString); } __int64 StringToInt64(const TCHAR *szString) { return _wtoi64(szString); } double StringToDouble(const TCHAR *szString) { return _wtof(szString); } long StringToLong(const TCHAR *szString) { return _wtol(szString); } ================================================ FILE: src/base/string_conv.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ int StringToInt(const TCHAR *szString); __int64 StringToInt64(const TCHAR *szString); double StringToDouble(const TCHAR *szString); long StringToLong(const TCHAR *szString); ================================================ FILE: src/base/string_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include #include #include "string_util.hh" // FIXME: Backslash in the name is missleading. TCHAR *IncludeTrailingBackslash(TCHAR *szPath) { int iLength = lstrlen(szPath); if (szPath[iLength - 1] != '\\' && szPath[iLength - 1] != '/') { szPath[iLength] = '\\'; szPath[iLength + 1] = '\0'; } return szPath; } // FIXME: Backslash in the name is missleading. TCHAR *ExcludeTrailingBackslash(TCHAR *szPath) { int iLength = lstrlen(szPath); if (szPath[iLength - 1] == '\\' || szPath[iLength - 1] == '/') szPath[iLength - 1] = '\0'; return szPath; } TCHAR *SubString(const TCHAR *szText,unsigned int uiStart,unsigned int uiLength) { TCHAR *szResult; int iLength = lstrlen(szText); if (!szText || (uiStart + uiLength > (unsigned int)iLength)) { szResult = new TCHAR[1]; szResult[0] = '\0'; return szResult; } szResult = new TCHAR[uiLength + 1]; unsigned int j = 0; for (unsigned int i = uiStart; i < uiStart + uiLength; i++,j++) szResult[j] = szText[i]; szResult[j] = '\0'; return szResult; } void FormatBytes(TCHAR *szBuffer,unsigned __int64 iBytes) { if (iBytes < 1024) swprintf(szBuffer,TEXT("%d %s"),(int)(iBytes & 0xFFFFFFFF),TEXT("Bytes")); else if (iBytes < 1024 * 1024) swprintf(szBuffer,TEXT("%.02f %s"),(double)iBytes/(1024.0),TEXT("KiB")); else if (iBytes < 1024 * 1024 * 1024) swprintf(szBuffer,TEXT("%.02f %s"),(double)iBytes/(1024.0 * 1024.0),TEXT("MiB")); else if (iBytes < (signed __int64)1024 * 1024 * 1024 * 1024) swprintf(szBuffer,TEXT("%.02f %s"),(double)iBytes/(1024.0 * 1024.0 * 1024.0),TEXT("GiB")); else swprintf(szBuffer,TEXT("%.02f %s"),(double)iBytes/(1024.0 * 1024.0 * 1024.0 * 1024.0),TEXT("TiB")); } /* Same as FormatBytes but does not include any decimals. */ void FormatBytesEx(TCHAR *szBuffer,unsigned __int64 iBytes) { if (iBytes < 1024) swprintf(szBuffer,TEXT("%d %s"),(int)(iBytes & 0xFFFFFFFF),TEXT("Bytes")); else if (iBytes < 1024 * 1024) swprintf(szBuffer,TEXT("%d %s"),(int)(iBytes/(1024.0)),TEXT("KiB")); else if (iBytes < 1024 * 1024 * 1024) swprintf(szBuffer,TEXT("%d %s"),(int)(iBytes/(1024.0 * 1024.0)),TEXT("MiB")); else if (iBytes < (signed __int64)1024 * 1024 * 1024 * 1024) swprintf(szBuffer,TEXT("%d %s"),(int)(iBytes/(1024.0 * 1024.0 * 1024.0)),TEXT("GiB")); else swprintf(szBuffer,TEXT("%d %s"),(int)(iBytes/(1024.0 * 1024.0 * 1024.0 * 1024.0)),TEXT("TiB")); } class CNumberFmt { private: TCHAR m_szDecimalSep[10]; TCHAR m_szThousandSep[10]; public: NUMBERFMT m_NumberFmt; void RetrieveDefaults(void); }; void CNumberFmt::RetrieveDefaults(void) { // Please avoid memset to clear the data structures, // as it confuses test software like BoundsChecker, // it's actually slower (!) and is not really portable. m_szDecimalSep[0] = _T('\0'); m_szThousandSep[0] = _T('\0'); m_NumberFmt.NumDigits = 0; m_NumberFmt.LeadingZero = 0; m_NumberFmt.Grouping = 0; m_NumberFmt.lpDecimalSep = m_szDecimalSep; m_NumberFmt.lpThousandSep = m_szThousandSep; m_NumberFmt.NegativeOrder = 0; ATLVERIFY(0 != GetLocaleInfo(LOCALE_USER_DEFAULT, LOCALE_IDIGITS | LOCALE_RETURN_NUMBER, LPTSTR(&m_NumberFmt.NumDigits), sizeof(m_NumberFmt.NumDigits) / sizeof(TCHAR))); ATLVERIFY(0 != GetLocaleInfo(LOCALE_USER_DEFAULT, LOCALE_ILZERO | LOCALE_RETURN_NUMBER, LPTSTR(&m_NumberFmt.LeadingZero), sizeof(m_NumberFmt.LeadingZero) / sizeof(TCHAR))); ATLVERIFY(0 != GetLocaleInfo(LOCALE_USER_DEFAULT, LOCALE_SDECIMAL, m_szDecimalSep, _countof(m_szDecimalSep))); ATLVERIFY(0 != GetLocaleInfo(LOCALE_USER_DEFAULT, LOCALE_STHOUSAND, m_szThousandSep, _countof( m_szThousandSep))); ATLVERIFY(0 != GetLocaleInfo(LOCALE_USER_DEFAULT, LOCALE_INEGNUMBER | LOCALE_RETURN_NUMBER, LPTSTR(&m_NumberFmt.NegativeOrder), sizeof(m_NumberFmt.NegativeOrder) / sizeof(TCHAR))); TCHAR szBuffer[100]; // Huge, but just in case. ATLVERIFY(0 != GetLocaleInfo(LOCALE_USER_DEFAULT, LOCALE_SGROUPING, szBuffer, _countof(szBuffer))); // Now the ugly part. Have to convert from something like string "3;2;0" to // int 32. for (const TCHAR *pParseGrpS = szBuffer; *pParseGrpS != _T('\0'); ++pParseGrpS) { if ((*pParseGrpS >= _T('1')) && (*pParseGrpS <= _T('9'))) m_NumberFmt.Grouping = m_NumberFmt.Grouping * 10 + (*pParseGrpS - _T('0')); if ((*pParseGrpS != _T('0')) && !pParseGrpS[1]) m_NumberFmt.Grouping *= 10; } } // Formats the given integer number according to the locale, adding for example // thousand separators. The only difference to the default formatting is that // no decimal digits are displayed. void FormatInteger(unsigned __int64 uiValue,TCHAR *szBuffer, unsigned uiBufferSize) { const unsigned MIN_CHAR_COUNT = 80; // The documentation for _ui64tot_s says 65 characters max. ATLASSERT(uiBufferSize >= MIN_CHAR_COUNT * 2); // We certainly need less than that, but I don't know exactly how much. TCHAR szNumber[MIN_CHAR_COUNT]; _ui64tot_s(uiValue,szNumber,_countof(szNumber),10); CNumberFmt Fmt; Fmt.RetrieveDefaults(); Fmt.m_NumberFmt.NumDigits = 0; ATLVERIFY(0 != GetNumberFormat(LOCALE_USER_DEFAULT, 0, szNumber, &Fmt.m_NumberFmt, szBuffer, uiBufferSize)); } int LastDelimiter(const TCHAR *szString,TCHAR cDelimiter) { int iLength = lstrlen(szString); for (int i = iLength - 1; i >= 0; i--) { if (szString[i] == cDelimiter) return i; } return -1; } int FirstDelimiter(const TCHAR *szString,TCHAR cDelimiter) { int iLength = lstrlen(szString); for (int i = 0; i < iLength; i++) { if (szString[i] == cDelimiter) return i; } return -1; } bool ExtractFilePath(TCHAR *szFileName) { int iLastDelimiter = LastDelimiter(szFileName,'\\'); if (LastDelimiter(szFileName,'/') > iLastDelimiter) iLastDelimiter = LastDelimiter(szFileName,'/'); if (iLastDelimiter == -1) return false; szFileName[iLastDelimiter + 1] = '\0'; return true; } bool ExtractFileName(TCHAR *szFileName) { int iLastDelimiter = LastDelimiter(szFileName,'\\'); if (LastDelimiter(szFileName,'/') > iLastDelimiter) iLastDelimiter = LastDelimiter(szFileName,'/'); if (iLastDelimiter == -1) return false; lstrcpy(szFileName,szFileName + (iLastDelimiter + 1)); return true; } bool ChangeFileExt(TCHAR *szFileName,const TCHAR *szFileExt) { unsigned int uiLastDelimiter = LastDelimiter(szFileName,'.'); const TCHAR *pFileExt = szFileExt; TCHAR *pFileName = szFileName + uiLastDelimiter; do { *pFileName = *pFileExt; *pFileName++; } while (*pFileExt++); return true; } void ForceSlashDelimiters(TCHAR *szFileName) { unsigned int uiLength = lstrlen(szFileName); for (unsigned int i = 0; i < uiLength; i++) { if (szFileName[i] == '\\') szFileName[i] = '/'; } } /* ComparePaths ------------ Works exactly like the strcmp function except that the path delimiters / and \ are concidered to be equal. */ int ComparePaths(const TCHAR *szPath1,const TCHAR *szPath2) { int iResult = 0; while (true) { while (!(iResult = *(unsigned char *)szPath1 - *(unsigned char *)szPath2) && *szPath2) ++szPath1,++szPath2; if (*(unsigned char *)szPath1 != '\\' && *(unsigned char *)szPath1 != '/') break; if (*(unsigned char *)szPath2 != '\\' && *(unsigned char *)szPath2 != '/') break; ++szPath1,++szPath2; } if (iResult < 0) iResult = -1; else if (iResult > 0) iResult = 1; return iResult; } /* TrimRight --------- Removes all white-spaces on the right side of a string. */ void TrimRight(TCHAR *szString) { for (int i = lstrlen(szString) - 1; i >= 0; i--) { if (szString[i] == ' ') szString[i] = '\0'; else break; } } void TrimLeft(ckcore::tstring &Str,const ckcore::tchar * const szCharsToRemove) { ckcore::tstring::size_type Pos = Str.find_first_not_of(szCharsToRemove); if (Pos != ckcore::tstring::npos) Str.erase(0,Pos); else Str.clear(); } void TrimRight(ckcore::tstring &Str,const ckcore::tchar * const szCharsToRemove) { ckcore::tstring::size_type Pos = Str.find_last_not_of(szCharsToRemove); if (Pos != ckcore::tstring::npos) Str.erase(Pos + 1); else Str.clear(); } /* SkipInteger ----------- Locates the end of the integer and return a pointer to that location. */ char *SkipInteger(char *szString) { // Skip all white spaces. while (*szString == ' ') *szString++; // Skip all digits. while (isdigit(*szString)) *szString++; return szString; } /* Converts an ANSI string into UTF-16 (BE). iTargetSize should be the size of szTarget counted in wchar_ts. */ void AnsiToUnicode(wchar_t *szTarget,const char *szSource,int iTargetSize) { int iConverted = MultiByteToWideChar(::AreFileApisANSI() ? CP_ACP : CP_OEMCP,MB_PRECOMPOSED, szSource,(int)strlen(szSource) + 1,szTarget,iTargetSize); if (iConverted == iTargetSize) szTarget[iTargetSize - 1] = '\0'; } /* Converts a UTF-16 (BE) string into ANSI. iTargetSize should be the size of szTarget counted in bytes. */ void UnicodeToAnsi(char *szTarget,const wchar_t *szSource,int iTargetSize) { int iConverted = WideCharToMultiByte(::AreFileApisANSI() ? CP_ACP : CP_OEMCP,0, szSource,(int)lstrlenW(szSource) + 1,szTarget,iTargetSize,NULL,NULL); if (iConverted == iTargetSize) szTarget[iTargetSize - 1] = '\0'; } ckcore::tstring GetCygwinFileName(const TCHAR *szFileName) { size_t uiLength = lstrlen(szFileName); ckcore::tstring CygPath; // Check if UNC path. if (uiLength > 2 && szFileName[0] == '\\' && szFileName[1] == '\\') { CygPath = szFileName; // Replace all backslashes by slashes. ckcore::tstring::iterator it; for (it = CygPath.begin(); it != CygPath.end(); it++) { TCHAR &c = *it; if (c == '\\') c = '/'; } } else // If not UNC path convert to proper cygwin path. { CygPath = _T("/cygdrive/"); // Copy the drive letter. CygPath.push_back(szFileName[0]); CygPath.push_back('/'); CygPath.append(szFileName + 3); // Replace all backslashes by slashes. ckcore::tstring::iterator it; for (it = CygPath.begin(); it != CygPath.end(); it++) { TCHAR &c = *it; if (c == '\\') c = '/'; } } return CygPath; } void GetCygwinFileName(const TCHAR *szFileName,TCHAR *szCygwinFileName) { // Check if UNC path. size_t uiLength = lstrlen(szFileName); if (uiLength > 2 && szFileName[0] == '\\' && szFileName[1] == '\\') { lstrcpy(szCygwinFileName,szFileName); // Replace all backslashes by slashes. for (size_t i = 0; i < uiLength; i++) { if (szCygwinFileName[i] == '\\') szCygwinFileName[i] = '/'; } } else // If not UNC path convert to proper cygwin path. { lstrcpy(szCygwinFileName,_T("/cygdrive/")); // Copy the drive letter. szCygwinFileName[10] = szFileName[0]; szCygwinFileName[11] = '/'; szCygwinFileName[12] = '\0'; lstrcat(szCygwinFileName,szFileName + 3); // Replace all backslashes by slashes. uiLength = lstrlen(szCygwinFileName); for (size_t i = 13; i < uiLength; i++) { if (szCygwinFileName[i] == '\\') szCygwinFileName[i] = '/'; } } } /* lsnprintf_s ----------- A secure version of lsprintf which does not allow buffer overruns and alwways terminates with a null character. */ void lsnprintf_s(TCHAR *szBuffer,int iBufferLength,const TCHAR *szFormatString,...) { va_list vlArgs; va_start(vlArgs,szFormatString); int iCount = _vsnwprintf(szBuffer,iBufferLength - 1,szFormatString,vlArgs); if (iCount < 0 || iCount == iBufferLength) szBuffer[iBufferLength - 1] = '\0'; } ================================================ FILE: src/base/string_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #ifndef _T #define _T TEXT #endif TCHAR *IncludeTrailingBackslash(TCHAR *szPath); TCHAR *ExcludeTrailingBackslash(TCHAR *szPath); TCHAR *SubString(const TCHAR *szText,unsigned int uiStart,unsigned int uiLength); void FormatBytes(TCHAR *szBuffer,unsigned __int64 iBytes); void FormatBytesEx(TCHAR *szBuffer,unsigned __int64 iBytes); void FormatInteger(unsigned __int64 uiValue,TCHAR *szBuffer,unsigned uiBufferSize); int LastDelimiter(const TCHAR *szString,TCHAR cDelimiter); int FirstDelimiter(const TCHAR *szString,TCHAR cDelimiter); bool ExtractFilePath(TCHAR *szFileName); bool ExtractFileName(TCHAR *szFileName); bool ChangeFileExt(TCHAR *szFileName,const TCHAR *szFileExt); void ForceSlashDelimiters(TCHAR *szFileName); int ComparePaths(const TCHAR *szPath1,const TCHAR *szPath2); void TrimRight(TCHAR *szString); void TrimRight(ckcore::tstring &Str,const ckcore::tchar * const szCharsToRemove); void TrimLeft(ckcore::tstring &Str,const ckcore::tchar * const szCharsToRemove); inline void TrimStr(ckcore::tstring &Str,const ckcore::tchar * const szCharsToRemove) { TrimRight(Str,szCharsToRemove); TrimLeft(Str,szCharsToRemove); } char *SkipInteger(char *szString); void AnsiToUnicode(wchar_t *szTarget,const char *szSource,int iTargetSize); void UnicodeToAnsi(char *szTarget,const wchar_t *szSource,int iTargetSize); void GetCygwinFileName(const TCHAR *szFileName,TCHAR *szCygwinFileName); ckcore::tstring GetCygwinFileName(const TCHAR *szFileName); void lsnprintf_s(TCHAR *szBuffer,int iBufferLength,const TCHAR *szFormatString,...); #define lstrncmp wcsncmp #define lsscanf swscanf #define lsprintf swprintf #define lstrncpy _tcsncpy #define lstrncat wcsncat ================================================ FILE: src/base/xml_processor.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include "xml_processor.hh" #include "string_conv.hh" const wchar_t CXmlProcessor::m_szXMLHeader[] = _T("\r\n"); CXmlProcessor::CXmlProcessor(eMode Mode) : m_Mode(Mode) { m_ulBufferSize = 0; m_ulBufferPos = 0; memset(m_ucBuffer,0,sizeof(m_ucBuffer)); m_pRoot = new CXmlElement(); lstrcpy(m_pRoot->m_szName,_T("Root")); // Set the current child to the root. m_pCurrent = m_pRoot; } CXmlProcessor::~CXmlProcessor() { delete m_pRoot; } void CXmlProcessor::DumpBuffer() { ckcore::File File(_T("xml_buffer_dump.txt")); if (File.open(ckcore::File::ckOPEN_WRITE)) File.write(m_ucBuffer,sizeof(m_ucBuffer)); } bool CXmlProcessor::ReadNext(ckcore::File &File,TCHAR &c) { if (m_ulBufferPos == m_ulBufferSize) { memset(m_ucBuffer,0,sizeof(m_ucBuffer)); ckcore::tint64 iRead = File.read(m_ucBuffer,sizeof(m_ucBuffer)); if (iRead == -1) return false; m_ulBufferSize = (unsigned long)iRead; m_ulBufferSize /= sizeof(TCHAR); m_ulBufferPos = 0; TCHAR sz; sz = true; if (m_ulBufferSize == 0) return false; } m_iRemainBytes -= sizeof(TCHAR); c = m_ucBuffer[m_ulBufferPos++]; return true; } void CXmlProcessor::ReadBack() { if (m_ulBufferPos > 0) { m_iRemainBytes += sizeof(TCHAR); m_ulBufferPos--; } } /* CXmlProcessor::ReadTagAttr ----------------------- Reads the current tag's attributes. It returns false if the element is empty and true if it's not. */ bool CXmlProcessor::ReadTagAttr(ckcore::File &File,CXmlElement *pElement) { TCHAR uc; if (!ReadNext(File,uc)) return false; CXmlAttribute *pAttr = new CXmlAttribute(); while (uc != '>') { // Check if this is an empty element. if (uc == '/') { if (!ReadNext(File,uc)) { delete pAttr; return false; } if (uc == '>') { delete pAttr; return false; } pAttr->m_szName.Append('/'); pElement->m_ulAttrLength++; } // Check if we have reached a ". In that case we expect a value. if (uc == '=') { pAttr->m_szName.Append('\0'); // Skip the first ". ReadNext(File,uc); ReadNext(File,uc); while (uc != '"') { pAttr->m_szValue.Append(uc); pElement->m_ulAttrLength++; if (!ReadNext(File,uc)) break; } pAttr->m_szValue.Append('\0'); pElement->m_Attributes.push_back(pAttr); // Allocate memory for the next attribute. pAttr = new CXmlAttribute(); } else { if (uc != ' ') { pAttr->m_szName.Append(uc); pElement->m_ulAttrLength++; } } if (!ReadNext(File,uc)) { delete pAttr; return false; } } delete pAttr; return true; } /* CXmlProcessor::ReadNextTag ----------------------- Reads the next tag in the file. It returns false if the element is empty and true if it's not. */ bool CXmlProcessor::ReadNextTag(ckcore::File &File,CXmlElement *pElement) { TCHAR uc; if (!ReadNext(File,uc)) return false; bool bResult = true; while (uc != '>') { if (uc == ' ') { bResult = ReadTagAttr(File,pElement); break; } pElement->m_szName.Append(uc); if (!ReadNext(File,uc)) return false; } pElement->m_szName.Append('\0'); return bResult; } /* CXmlProcessor::Load ------------------- Loads the specified XML into a tree structure in memory. Varius return values. */ int CXmlProcessor::Load(const TCHAR *szFullPath) { // Open the file. ckcore::File File(szFullPath); if (!File.open(ckcore::File::ckOPEN_READ)) return XMLRES_FILEERROR; // If the application is in an unicode environment we need to check what // byte-order us used. unsigned short usBOM = 0; if (File.read(&usBOM,2) == -1) return XMLRES_FILEERROR; switch (usBOM) { // Currently the only supported byte-order. case BOM_UTF32BE: break; case BOM_UTF8: case BOM_UTF32LE: case BOM_SCSU: return XMLRES_UNSUPBOM; default: // If no BOM is found the file pointer has to be re-moved to the beginning. if (File.seek(0,ckcore::File::ckFILE_BEGIN) == -1) return XMLRES_FILEERROR; break; }; // Clear the root. m_pRoot->Clear(); CXmlElement *pCurElem = m_pRoot; // Set the current child to the root. m_pCurrent = m_pRoot; m_iRemainBytes = File.size(); unsigned int uiDataPos = 0; bool bHandleData = false; while (m_iRemainBytes) { TCHAR uc; if (!ReadNext(File,uc)) break; // We have found the beginning of a tag. if (uc == '<') { if (!ReadNext(File,uc)) break; // Check if we have reached the end of a section. if (uc == '/') { CCustomString szTemp(XML_NAMELENGTH); if (!ReadNext(File,uc)) break; while (uc != '>') { szTemp.Append(uc); if (!ReadNext(File,uc)) break; } szTemp.Append('\0'); if (lstrcmp(pCurElem->m_szName,szTemp)) { return XMLRES_BADSYNC; } else { bHandleData = false; if (uiDataPos != 0) { pCurElem->m_szData.Append('\0'); uiDataPos = 0; } pCurElem = pCurElem->m_pParent; } } else if (uc == '?') // Check if we have reached a processing unstruction. { TCHAR cTemp; if (!ReadNext(File,cTemp)) break; while (cTemp != '>') { if (!ReadNext(File,cTemp)) break; } } else { ReadBack(); if (uiDataPos != 0) { pCurElem->m_szData.Append('\0'); uiDataPos = 0; } // Add the new element. CXmlElement *pNewElem = new CXmlElement(); pNewElem->m_pParent = pCurElem; bHandleData = ReadNextTag(File,pNewElem); if (pCurElem != NULL) pCurElem->m_Children.push_back(pNewElem); if (bHandleData) pCurElem = pNewElem; } } else { // Filter some characters. if (uc == '\t' || uc == '\n' || uc == '\r') continue; pCurElem->m_szData.Append(uc); uiDataPos++; } } return XMLRES_OK; } void CXmlProcessor::SaveEntity(ckcore::File &File,unsigned int uiIndent,CXmlElement *pElement) { // If the element contains no information we skip it. if (pElement->m_Children.size() == 0 && /*pElement->m_szAttr[0] == '\0' &&*/ pElement->m_Attributes.size() == 0 && pElement->m_szData[0] == '\0') { return; } // The length of the complete attributes string when printed to the buffer. unsigned long ulAttrLength = pElement->m_ulAttrLength + (unsigned long)pElement->m_Attributes.size() * 4; // The epsilon value compensates for some <, > and / characters. TCHAR *szOutBuf = new TCHAR[ pElement->m_szName.Length() * 2 + pElement->m_szData.Length() + ulAttrLength + uiIndent + XML_OUTBUF_EPSILON]; unsigned int i = 0; // Indent. for (i = 0; i < uiIndent; i++) szOutBuf[i] = '\t'; szOutBuf[i++] = '<'; szOutBuf[i] = '\0'; // Name. lstrcat(szOutBuf,pElement->m_szName); // Attributes. for (i = 0; i < pElement->m_Attributes.size(); i++) { lstrcat(szOutBuf,_T(" ")); lstrcat(szOutBuf,pElement->m_Attributes[i]->m_szName); lstrcat(szOutBuf,_T("=\"")); lstrcat(szOutBuf,pElement->m_Attributes[i]->m_szValue); lstrcat(szOutBuf,_T("\"")); } // End of the tag. if (pElement->m_Children.size() != 0) { if (pElement->m_szData[0] == '\0') lstrcat(szOutBuf,_T(">\r\n")); else lstrcat(szOutBuf,_T(">")); } else { if (pElement->m_szData[0] == '\0') lstrcat(szOutBuf,_T("/>\r\n")); else lstrcat(szOutBuf,_T(">")); } // Write to the file. File.write(szOutBuf,lstrlen(szOutBuf) * sizeof(TCHAR)); // Write the data. if (pElement->m_szData[0] != '\0') { lstrcpy(szOutBuf,pElement->m_szData); // ... if (pElement->m_Children.size() != 0) lstrcat(szOutBuf,_T("\r\n")); // ... File.write(szOutBuf,lstrlen(szOutBuf) * sizeof(TCHAR)); } // Traverse the children. for (i = 0; i < pElement->m_Children.size(); i++) SaveEntity(File,uiIndent + 1,pElement->m_Children[i]); // Re-indent if necessary. if (pElement->m_Children.size() != 0) { for (i = 0; i < uiIndent; i++) szOutBuf[i] = '\t'; } else { i = 0; } // If the element has data or has children we should include a full termination tag. if (pElement->m_szData[0] != '\0' || pElement->m_Children.size() != 0) { szOutBuf[i++] = '<'; szOutBuf[i++] = '/'; szOutBuf[i] = '\0'; lstrcat(szOutBuf,pElement->m_szName); lstrcat(szOutBuf,_T(">\r\n")); File.write(szOutBuf,lstrlen(szOutBuf) * sizeof(TCHAR)); } delete [] szOutBuf; } /* CXmlProcessor::Save ------------------- Saves the current loaded XML-structure to a file with the specified filename. Various return values. */ int CXmlProcessor::Save(const TCHAR *szFullPath) { // Open the file. ckcore::File File(szFullPath); if (!File.open(ckcore::File::ckOPEN_WRITE)) return XMLRES_FILEERROR; // Write byte-order mark. #ifdef XML_SAVE_BOM unsigned short usBOM = BOM_UTF32BE; if (File.write(&usBOM,2) == -1) { File.remove(); return XMLRES_FILEERROR; } #endif // Write the header. if (File.write((void *)m_szXMLHeader,lstrlen(m_szXMLHeader) * sizeof(TCHAR)) == -1) { File.remove(); return XMLRES_FILEERROR; } for (unsigned int i = 0; i < m_pRoot->m_Children.size(); i++) SaveEntity(File,0,m_pRoot->m_Children[i]); return XMLRES_OK; } /* XMLProcessor::EnterElement -------------------------- Enters the specified element if it exists. True is returned upon success, false if the specified element was not found. */ bool CXmlProcessor::EnterElement(const TCHAR *szName) { for (unsigned int i = 0; i < m_pCurrent->m_Children.size(); i++) { if (!lstrcmp(m_pCurrent->m_Children[i]->m_szName,szName)) { m_pCurrent = m_pCurrent->m_Children[i]; return true; } } return false; } bool CXmlProcessor::EnterElement(unsigned int uiIndex) { if (uiIndex >= m_pCurrent->m_Children.size()) return false; m_pCurrent = m_pCurrent->m_Children[uiIndex]; return true; } /* CXmlProcessor::LeaveElement --------------------------- Leaves the current element. True is returned if the operation was successful, otherwise false is returned. */ bool CXmlProcessor::LeaveElement() { if (m_pCurrent->m_pParent != NULL) { m_pCurrent = m_pCurrent->m_pParent; return true; } return false; } unsigned int CXmlProcessor::GetElementChildCount() { return (unsigned int)m_pCurrent->m_Children.size(); } bool CXmlProcessor::GetElementAttrValue(const TCHAR *szAttrName,TCHAR *&szValue) { for (unsigned int i = 0; i < m_pCurrent->m_Attributes.size(); i++) { if (!lstrcmp(m_pCurrent->m_Attributes[i]->m_szName,szAttrName)) { szValue = m_pCurrent->m_Attributes[i]->m_szValue; return true; } } return false; } void CXmlProcessor::GetSafeElementAttrValue(const TCHAR *szAttrName,TCHAR *szValue,int iMaxLength) { TCHAR *szData = NULL; if (GetElementAttrValue(szAttrName,szData) && lstrlen(szData) < iMaxLength) lstrcpy(szValue,szData); } void CXmlProcessor::GetSafeElementAttrValue(const TCHAR *szAttrName,bool *pValue) { TCHAR *szData = NULL; if (GetElementAttrValue(szAttrName,szData)) *pValue = StringToInt(szData) != 0; } void CXmlProcessor::GetSafeElementAttrValue(const TCHAR *szAttrName,int *pValue) { TCHAR *szData = NULL; if (GetElementAttrValue(szAttrName,szData)) *pValue = StringToInt(szData); } void CXmlProcessor::GetSafeElementAttrValue(const TCHAR *szAttrName,__int64 *pValue) { TCHAR *szData = NULL; if (GetElementAttrValue(szAttrName,szData)) *pValue = StringToInt64(szData); } void CXmlProcessor::GetSafeElementAttrValue(const TCHAR *szAttrName,double *pValue) { TCHAR *szData = NULL; if (GetElementAttrValue(szAttrName,szData)) *pValue = StringToDouble(szData); } void CXmlProcessor::GetSafeElementAttrValue(const TCHAR *szAttrName,long *pValue) { TCHAR *szData = NULL; if (GetElementAttrValue(szAttrName,szData)) *pValue = StringToLong(szData); } bool CXmlProcessor::GetElementData(TCHAR *&szData) { if (m_pCurrent->m_szData[0] == '\0') return false; szData = m_pCurrent->m_szData; return true; } void CXmlProcessor::GetSafeElementData(const TCHAR *szName,TCHAR *pData,int iMaxLength) { if (EnterElement(szName)) { TCHAR *szData = NULL; if (GetElementData(szData)) { if (lstrlen(szData) < iMaxLength) lstrcpy(pData,szData); } LeaveElement(); } } void CXmlProcessor::GetSafeElementData(const TCHAR *szName,bool *pData) { if (EnterElement(szName)) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToInt(szData) != 0; LeaveElement(); } } void CXmlProcessor::GetSafeElementData(const TCHAR *szName,int *pData) { if (EnterElement(szName)) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToInt(szData); LeaveElement(); } } void CXmlProcessor::GetSafeElementData(const TCHAR *szName,__int64 *pData) { if (EnterElement(szName)) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToInt64(szData); LeaveElement(); } } void CXmlProcessor::GetSafeElementData(const TCHAR *szName,double *pData) { if (EnterElement(szName)) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToDouble(szData); LeaveElement(); } } void CXmlProcessor::GetSafeElementData(const TCHAR *szName,long *pData) { if (EnterElement(szName)) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToLong(szData); LeaveElement(); } } void CXmlProcessor::GetSafeElementData(TCHAR *pData) { TCHAR *szData = NULL; if (GetElementData(szData)) lstrcpy(pData,szData); } void CXmlProcessor::GetSafeElementData(bool *pData) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToInt(szData) != 0; } void CXmlProcessor::GetSafeElementData(int *pData) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToInt(szData); } void CXmlProcessor::GetSafeElementData(__int64 *pData) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToInt64(szData); } void CXmlProcessor::GetSafeElementData(double *pData) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToDouble(szData); } void CXmlProcessor::GetSafeElementData(long *pData) { TCHAR *szData = NULL; if (GetElementData(szData)) *pData = StringToLong(szData); } bool CXmlProcessor::AddElement(const TCHAR *szName,const TCHAR *szData,bool bEnter) { CXmlElement *pNewElem = new CXmlElement(lstrlen(szName) + 1,lstrlen(szData) + 1); if (!pNewElem) return false; pNewElem->m_pParent = m_pCurrent; pNewElem->m_szName.CopyFrom(szName); if (m_Mode == MODE_HTML) pNewElem->m_szData.CopyFromHtml(szData); else pNewElem->m_szData.CopyFrom(szData); m_pCurrent->m_Children.push_back(pNewElem); if (bEnter) m_pCurrent = pNewElem; return true; } bool CXmlProcessor::AddElement(const TCHAR *szName,bool bData,bool bEnter) { return AddElement(szName,(int)bData,bEnter); } bool CXmlProcessor::AddElement(const TCHAR *szName,int iData,bool bEnter) { TCHAR szTemp[16]; _itow(iData,szTemp,10); return AddElement(szName,szTemp,bEnter); } bool CXmlProcessor::AddElement(const TCHAR *szName,__int64 iData,bool bEnter) { TCHAR szTemp[32]; _i64tow(iData,szTemp,10); return AddElement(szName,szTemp,bEnter); } bool CXmlProcessor::AddElement(const TCHAR *szName,double dData,bool bEnter) { TCHAR szTemp[32]; swprintf(szTemp,_T("%f"),dData); return AddElement(szName,szTemp,bEnter); } bool CXmlProcessor::AddElement(const TCHAR *szName,long lData,bool bEnter) { TCHAR szTemp[16]; _ltow(lData,szTemp,10); return AddElement(szName,szTemp,bEnter); } bool CXmlProcessor::AddElementAttr(const TCHAR *szAttrName,const TCHAR *szValue) { CXmlAttribute *pNewAttr = new CXmlAttribute(lstrlen(szAttrName) + 1,lstrlen(szValue) + 1); if (!pNewAttr) return false; pNewAttr->m_szName.CopyFrom(szAttrName); if (m_Mode == MODE_HTML) pNewAttr->m_szValue.CopyFromHtml(szValue); else pNewAttr->m_szValue.CopyFrom(szValue); m_pCurrent->m_Attributes.push_back(pNewAttr); m_pCurrent->m_ulAttrLength += lstrlen(szAttrName) + lstrlen(szValue); return true; } bool CXmlProcessor::AddElementAttr(const TCHAR *szAttrName,bool bValue) { return AddElementAttr(szAttrName,(int)bValue); } bool CXmlProcessor::AddElementAttr(const TCHAR *szAttrName,int iValue) { TCHAR szTemp[16]; _itow(iValue,szTemp,10); return AddElementAttr(szAttrName,szTemp); } bool CXmlProcessor::AddElementAttr(const TCHAR *szAttrName,__int64 iValue) { TCHAR szTemp[32]; _i64tow(iValue,szTemp,10); return AddElementAttr(szAttrName,szTemp); } bool CXmlProcessor::AddElementAttr(const TCHAR *szAttrName,double dValue) { TCHAR szTemp[32]; swprintf(szTemp,_T("%f"),dValue); return AddElementAttr(szAttrName,szTemp); } bool CXmlProcessor::AddElementAttr(const TCHAR *szAttrName,long lValue) { TCHAR szTemp[16]; _ltow(lValue,szTemp,10); return AddElementAttr(szAttrName,szTemp); } ================================================ FILE: src/base/xml_processor.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include "custom_string.hh" #define BOM_UTF8 0xEFBBBF #define BOM_UTF32BE 0x0000FEFF #define BOM_UTF32LE 0xFFFE0000 #define BOM_SCSU 0x0EFEFF #define XML_NAMELENGTH 128 //#define XML_ATTRLENGTH 256 #define XML_DATALENGTH 256 // ... #define XML_ATTR_NAMELENGTH 32 #define XML_ATTR_VALUELENGTH 16 // ... #define XML_OUTBUF_EPSILON 16 #define XML_BUFFER_SIZE 1024 #define XML_SAVE_BOM // Return values. #define XMLRES_FAIL 0x00 #define XMLRES_OK 0x01 #define XMLRES_BADSYNC 0x02 #define XMLRES_FILEERROR 0x03 #define XMLRES_UNSUPBOM 0x04 class CXmlAttribute { public: CCustomString m_szName; CCustomString m_szValue; CXmlAttribute() : m_szName(XML_ATTR_NAMELENGTH), m_szValue(XML_ATTR_VALUELENGTH) { } CXmlAttribute(unsigned int uiNameLength,unsigned int uiValueLength) : m_szName(uiNameLength), m_szValue(uiValueLength) { } }; class CXmlElement { public: CCustomString m_szName; CCustomString m_szData; unsigned long m_ulAttrLength; std::vector m_Attributes; std::vector m_Children; CXmlElement *m_pParent; CXmlElement() : m_szName(XML_NAMELENGTH), m_szData(XML_DATALENGTH) { m_szName[0] = '\0'; m_szData[0] = '\0'; m_ulAttrLength = 0; } CXmlElement(unsigned int uiNameLength,unsigned int uiDataLength) : m_szName(uiNameLength), m_szData(uiDataLength) { m_szName[0] = '\0'; m_szData[0] = '\0'; m_ulAttrLength = 0; } ~CXmlElement() { Clear(); } void Clear() { // Free the children. for (unsigned int iIndex = 0; iIndex < m_Children.size(); iIndex++) { // Remove the object from m_Instances. std::vector ::iterator itObject = m_Children.begin() + iIndex; delete *itObject; } m_Children.clear(); // ... for (unsigned int iIndex = 0; iIndex < m_Attributes.size(); iIndex++) { // Remove the object from m_Instances. std::vector ::iterator itObject = m_Attributes.begin() + iIndex; delete *itObject; } m_Children.clear(); } }; class CXmlProcessor { public: enum eMode { MODE_NORMAL, MODE_HTML }; private: eMode m_Mode; TCHAR m_ucBuffer[XML_BUFFER_SIZE]; unsigned long m_ulBufferSize; unsigned long m_ulBufferPos; __int64 m_iRemainBytes; CXmlElement *m_pRoot; CXmlElement *m_pCurrent; void DumpBuffer(); bool ReadNext(ckcore::File &File,TCHAR &c); void ReadBack(); bool ReadTagAttr(ckcore::File &File,CXmlElement *pElement); bool ReadNextTag(ckcore::File &File,CXmlElement *pElement); void SaveEntity(ckcore::File &File,unsigned int uiIndent,CXmlElement *pElement); static const wchar_t m_szXMLHeader[]; public: CXmlProcessor(eMode Mode = MODE_NORMAL); ~CXmlProcessor(); int Load(const TCHAR *szFullPath); int Save(const TCHAR *szFullPath); bool EnterElement(const TCHAR *szName); bool EnterElement(unsigned int uiIndex); bool LeaveElement(); unsigned int GetElementChildCount(); bool GetElementAttrValue(const TCHAR *szAttrName,TCHAR *&szValue); void GetSafeElementAttrValue(const TCHAR *szAttrName,TCHAR *szValue,int iMaxLength); void GetSafeElementAttrValue(const TCHAR *szAttrName,bool *pValue); void GetSafeElementAttrValue(const TCHAR *szAttrName,int *pValue); void GetSafeElementAttrValue(const TCHAR *szAttrName,__int64 *pValue); void GetSafeElementAttrValue(const TCHAR *szAttrName,double *pValue); void GetSafeElementAttrValue(const TCHAR *szAttrName,long *pValue); bool GetElementData(TCHAR *&szData); void GetSafeElementData(const TCHAR *szName,TCHAR *pData,int iMaxLength); void GetSafeElementData(const TCHAR *szName,bool *pData); void GetSafeElementData(const TCHAR *szName,int *pData); void GetSafeElementData(const TCHAR *szName,__int64 *pData); void GetSafeElementData(const TCHAR *szName,double *pData); void GetSafeElementData(const TCHAR *szName,long *pData); void GetSafeElementData(TCHAR *pData); void GetSafeElementData(bool *pData); void GetSafeElementData(int *pData); void GetSafeElementData(__int64 *pData); void GetSafeElementData(double *pData); void GetSafeElementData(long *pData); bool AddElement(const TCHAR *szName,const TCHAR *szData,bool bEnter = false); bool AddElement(const TCHAR *szName,bool bData,bool bEnter = false); bool AddElement(const TCHAR *szName,int iData,bool bEnter = false); bool AddElement(const TCHAR *szName,__int64 iData,bool bEnter = false); bool AddElement(const TCHAR *szName,double dData,bool bEnter = false); bool AddElement(const TCHAR *szName,long uData,bool bEnter = false); bool AddElementAttr(const TCHAR *szAttrName,const TCHAR *szValue); bool AddElementAttr(const TCHAR *szAttrName,bool bValue); bool AddElementAttr(const TCHAR *szAttrName,int iValue); bool AddElementAttr(const TCHAR *szAttrName,__int64 iValue); bool AddElementAttr(const TCHAR *szAttrName,double dValue); bool AddElementAttr(const TCHAR *szAttrName,long lValue); }; ================================================ FILE: src/codecs/lame/config_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "config_dlg.hh" CConfigDlg::CConfigDlg(CEncoderConfig *pConfig) : CPropertySheetImpl(_T("Configuration"),0,NULL) { m_bCentered = false; m_psh.dwFlags |= PSH_NOAPPLYNOW; m_GeneralPage.SetConfig(pConfig); AddPage(m_GeneralPage); } CConfigDlg::~CConfigDlg() { } LRESULT CConfigDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } bHandled = FALSE; return 0; } ================================================ FILE: src/codecs/lame/config_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "config_general_page.hh" class CConfigDlg : public CPropertySheetImpl { private: bool m_bCentered; CConfigGeneralPage m_GeneralPage; public: CConfigDlg(CEncoderConfig *pConfig); ~CConfigDlg(); BEGIN_MSG_MAP(CConfigDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/codecs/lame/config_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "config_general_page.hh" CConfigGeneralPage::CConfigGeneralPage() { m_pConfig = NULL; } CConfigGeneralPage::~CConfigGeneralPage() { } bool CConfigGeneralPage::SetConfig(CEncoderConfig *pConfig) { if (pConfig == NULL) return false; m_pConfig = pConfig; return true; } bool CConfigGeneralPage::OnApply() { m_pConfig->m_bMono = IsDlgButtonChecked(IDC_MONOCHECK) == TRUE; m_pConfig->m_bBitrateMode = IsDlgButtonChecked(IDC_BITRATERADIO) == TRUE; m_pConfig->m_bConstantBitrate = IsDlgButtonChecked(IDC_BITRATECHECK) == TRUE; m_pConfig->m_bFastVBR = m_VBRModeComboBox.GetCurSel() == 1; m_pConfig->m_iPreset = m_PresetComboBox.GetCurSel(); m_pConfig->m_iEncodeQuality = m_EncQualityComboBox.GetCurSel(); m_pConfig->m_iBitrate = m_BitrateTrackBar.GetPos(); m_pConfig->m_iQuality = m_QualityTrackBar.GetPos(); return true; } LRESULT CConfigGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Fill the preset combo box. m_PresetComboBox = GetDlgItem(IDC_PRESETCOMBO); m_PresetComboBox.AddString(_T("Custom")); m_PresetComboBox.AddString(_T("Medium (VBR 150-180 kbps)")); m_PresetComboBox.AddString(_T("Standard (VBR 170-210 kbps)")); m_PresetComboBox.AddString(_T("Extreme (VBR 200-240 kbps)")); m_PresetComboBox.AddString(_T("Insane (CBR 320 kbps)")); m_PresetComboBox.SetCurSel(m_pConfig->m_iPreset); // Fill the encode quality combo box. m_EncQualityComboBox = GetDlgItem(IDC_ENCODEQUALITYCOMBO); m_EncQualityComboBox.AddString(_T("Fast")); m_EncQualityComboBox.AddString(_T("Standard")); m_EncQualityComboBox.AddString(_T("High")); m_EncQualityComboBox.SetCurSel(m_pConfig->m_iEncodeQuality); // Fill the VBR mode combo box. m_VBRModeComboBox = GetDlgItem(IDC_VBRMODECOMBO); m_VBRModeComboBox.AddString(_T("Standard")); m_VBRModeComboBox.AddString(_T("Fast")); m_VBRModeComboBox.SetCurSel((int)m_pConfig->m_bFastVBR); // Perform a Windows XP theme check here to move the radio button. /*CStatic BitrateStatic = GetDlgItem(IDC_BITRATESTATIC); RECT rcWindow; BitrateStatic.GetWindowRect(&rcWindow); ScreenToClient(&rcWindow); rcWindow.left -= 2; BitrateStatic.MoveWindow(&rcWindow);*/ // Setup the bitrate slider. m_BitrateTrackBar = GetDlgItem(IDC_BITRATESLIDER); m_BitrateTrackBar.SetRange(8,320); m_BitrateTrackBar.SetPageSize(8); m_BitrateTrackBar.SetLineSize(8); m_BitrateTrackBar.SetTic(16); m_BitrateTrackBar.SetTic(24); m_BitrateTrackBar.SetTic(32); m_BitrateTrackBar.SetTic(40); m_BitrateTrackBar.SetTic(48); m_BitrateTrackBar.SetTic(56); m_BitrateTrackBar.SetTic(64); m_BitrateTrackBar.SetTic(80); m_BitrateTrackBar.SetTic(96); m_BitrateTrackBar.SetTic(112); m_BitrateTrackBar.SetTic(128); m_BitrateTrackBar.SetTic(144); m_BitrateTrackBar.SetTic(160); m_BitrateTrackBar.SetTic(192); m_BitrateTrackBar.SetTic(224); m_BitrateTrackBar.SetTic(256); m_BitrateTrackBar.SetPos(m_pConfig->m_iBitrate); // Setup the quality slider. m_QualityTrackBar = GetDlgItem(IDC_QUALITYSLIDER); m_QualityTrackBar.SetRange(0,9); m_QualityTrackBar.SetPos(m_pConfig->m_iQuality); // We select the bitrate mode by default. if (m_pConfig->m_bBitrateMode) CheckDlgButton(IDC_BITRATERADIO,BST_CHECKED); else CheckDlgButton(IDC_QUALITYRADIO,BST_CHECKED); SelectBitrateMode(m_pConfig->m_bBitrateMode); // Select the default (standard) preset. SelectPreset(m_pConfig->m_iPreset); return TRUE; } LRESULT CConfigGeneralPage::OnHScroll(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { if (IsDlgButtonChecked(IDC_BITRATERADIO) && LOWORD(wParam) == TB_THUMBTRACK) { unsigned int uiPos = HIWORD(wParam); // Jump to the closest position that have a tic. if (uiPos < 71) { uiPos >>= 3; uiPos <<= 3; } else if (uiPos < 175) { uiPos >>= 4; uiPos <<= 4; } else if (uiPos < 287) { uiPos >>= 5; uiPos <<= 5; } else { uiPos = 320; } m_BitrateTrackBar.SetPos(uiPos); } bHandled = false; return TRUE; } void CConfigGeneralPage::SelectBitrateMode(BOOL bSelect) { ::EnableWindow(GetDlgItem(IDC_QUALITYSTATIC),!bSelect); ::EnableWindow(GetDlgItem(IDC_QUALITYSLIDER),!bSelect); ::EnableWindow(GetDlgItem(IDC_QUALITYHIGHSTATIC),!bSelect); ::EnableWindow(GetDlgItem(IDC_QUALITYLOWSTATIC),!bSelect); ::EnableWindow(GetDlgItem(IDC_VBRMODESTATIC),!bSelect); ::EnableWindow(GetDlgItem(IDC_VBRMODECOMBO),!bSelect); ::EnableWindow(GetDlgItem(IDC_BITRATESTATIC),bSelect); ::EnableWindow(GetDlgItem(IDC_BITRATESLIDER),bSelect); ::EnableWindow(GetDlgItem(IDC_BITRATE8STATIC),bSelect); ::EnableWindow(GetDlgItem(IDC_BITRATE64STATIC),bSelect); ::EnableWindow(GetDlgItem(IDC_BITRATE128STATIC),bSelect); ::EnableWindow(GetDlgItem(IDC_BITRATE192STATIC),bSelect); ::EnableWindow(GetDlgItem(IDC_BITRATE320STATIC),bSelect); ::EnableWindow(GetDlgItem(IDC_BITRATECHECK),bSelect); } void CConfigGeneralPage::SelectPreset(int iPreset) { if (iPreset != CONFIG_PRESET_CUSTOM) { ::EnableWindow(GetDlgItem(IDC_QUALITYSTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_QUALITYSLIDER),FALSE); ::EnableWindow(GetDlgItem(IDC_QUALITYHIGHSTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_QUALITYLOWSTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_VBRMODESTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_VBRMODECOMBO),FALSE); ::EnableWindow(GetDlgItem(IDC_BITRATESTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_BITRATESLIDER),FALSE); ::EnableWindow(GetDlgItem(IDC_BITRATE8STATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_BITRATE64STATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_BITRATE128STATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_BITRATE192STATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_BITRATE320STATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_BITRATECHECK),FALSE); // Controls not covered by the SelectBitrateMode function. ::EnableWindow(GetDlgItem(IDC_BITRATERADIO),FALSE); ::EnableWindow(GetDlgItem(IDC_QUALITYRADIO),FALSE); ::EnableWindow(GetDlgItem(IDC_ENCODEQUALITYSTATIC),FALSE); ::EnableWindow(GetDlgItem(IDC_ENCODEQUALITYCOMBO),FALSE); ::EnableWindow(GetDlgItem(IDC_MONOCHECK),FALSE); } else { SelectBitrateMode(IsDlgButtonChecked(IDC_BITRATERADIO)); // Controls not covered by the SelectBitrateMode function. ::EnableWindow(GetDlgItem(IDC_BITRATERADIO),TRUE); ::EnableWindow(GetDlgItem(IDC_QUALITYRADIO),TRUE); ::EnableWindow(GetDlgItem(IDC_ENCODEQUALITYSTATIC),TRUE); ::EnableWindow(GetDlgItem(IDC_ENCODEQUALITYCOMBO),TRUE); ::EnableWindow(GetDlgItem(IDC_MONOCHECK),TRUE); } } LRESULT CConfigGeneralPage::OnBitrateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CheckDlgButton(IDC_QUALITYRADIO,BST_UNCHECKED); SelectBitrateMode(TRUE); bHandled = false; return TRUE; } LRESULT CConfigGeneralPage::OnQualityCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CheckDlgButton(IDC_BITRATERADIO,BST_UNCHECKED); SelectBitrateMode(FALSE); bHandled = false; return TRUE; } LRESULT CConfigGeneralPage::OnPresetChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { SelectPreset(m_PresetComboBox.GetCurSel()); return 0; } ================================================ FILE: src/codecs/lame/config_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #define CONFIG_PRESET_CUSTOM 0 #define CONFIG_PRESET_MEDIUM 1 #define CONFIG_PRESET_STANDARD 2 #define CONFIG_PRESET_EXTREME 3 #define CONFIG_PRESET_INSANE 4 #define CONFIG_EQ_FAST 0 #define CONFIG_EQ_STANDARD 1 #define CONFIG_EQ_HIGH 2 class CEncoderConfig { public: CEncoderConfig() { m_bMono = false; m_bBitrateMode = true; m_bConstantBitrate = false; m_bFastVBR = false; m_iPreset = CONFIG_PRESET_STANDARD; m_iEncodeQuality = CONFIG_EQ_STANDARD; m_iBitrate = 192; m_iQuality = 4; } bool m_bMono; bool m_bBitrateMode; bool m_bConstantBitrate; bool m_bFastVBR; int m_iPreset; int m_iEncodeQuality; int m_iBitrate; int m_iQuality; }; class CConfigGeneralPage : public CPropertyPageImpl { private: CComboBox m_PresetComboBox; CComboBox m_EncQualityComboBox; CComboBox m_VBRModeComboBox; CTrackBarCtrl m_BitrateTrackBar; CTrackBarCtrl m_QualityTrackBar; void SelectBitrateMode(BOOL bSelect); void SelectPreset(int iPreset); CEncoderConfig *m_pConfig; public: enum { IDD = IDD_PROPPAGE_CONFIGGENERAL }; CConfigGeneralPage(); ~CConfigGeneralPage(); bool SetConfig(CEncoderConfig *pConfig); bool OnApply(); BEGIN_MSG_MAP(CConfigGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_HSCROLL,OnHScroll) COMMAND_ID_HANDLER(IDC_BITRATERADIO,OnBitrateCheck) COMMAND_ID_HANDLER(IDC_QUALITYRADIO,OnQualityCheck) COMMAND_HANDLER(IDC_PRESETCOMBO,CBN_SELCHANGE,OnPresetChange) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnHScroll(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnBitrateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnQualityCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnPresetChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/codecs/lame/lame.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "config_dlg.hh" #include "lame_encoder.hh" // Capability flags. int capabilities = IRC_HAS_ENCODER | IRC_HAS_CONFIG; // Version and about strings. TCHAR *str_version = _T("0.53.0.0"); TCHAR *str_about = _T("InfraRecorder MP3 Encoder\n\nCopyright 2006-2012 Christian Kindahl.\n\nThis codec is using the libmp3lame (LAME) library.\nVisit: http://lame.sourceforge.net/ for more information.\n\nPlease note that personal and/or commercial use of\ncompiled versions of this codec requires a patent license\nin some countries. Please check before using this codec."); TCHAR *str_encoder = _T("MP3"); TCHAR *str_file_ext = _T(".mp3"); // Global variables. LameEncoder *lame_encoder = NULL; // Encoder configuration. CEncoderConfig encoder_cfg; BOOL APIENTRY DllMain(HANDLE hModule,DWORD ul_reason_for_call,LPVOID lpReserved) { return TRUE; } /** * Returns bit information on what operations that are supported by the codec. * @return Bit information on what operations that are supported by the codec. */ int WINAPI irc_capabilities() { return capabilities; } TCHAR *WINAPI irc_string(unsigned int uiID) { switch (uiID) { case IRC_STR_VERSION: return str_version; case IRC_STR_ABOUT: return str_about; case IRC_STR_ENCODER: return str_encoder; case IRC_STR_FILEEXT: return str_file_ext; } return NULL; } bool WINAPI irc_set_callback(tirc_send_message *pSendMessage) { if (pSendMessage == NULL) return false; LameBase::set_callback(pSendMessage); return true; } bool WINAPI irc_decode_init(const TCHAR *szFileName,int &iNumChannels, int &iSampleRate,int &iBitRate, unsigned __int64 &uiDuration) { return false; } __int64 WINAPI irc_decode_process(unsigned char *pBuffer,__int64 iBufferSize, unsigned __int64 &uiTime) { return -1; } bool WINAPI irc_decode_exit() { return false; } bool WINAPI irc_encode_init(const TCHAR *szFileName,int iNumChannels, int iSampleRate,int iBitRate) { if (lame_encoder != NULL) return false; lame_encoder = new LameEncoder(szFileName,iNumChannels,iSampleRate,iBitRate,encoder_cfg); if (!lame_encoder->initialize()) { delete lame_encoder; lame_encoder = NULL; return false; } return true; } __int64 WINAPI irc_encode_process(unsigned char *pBuffer,__int64 iDataSize) { if (lame_encoder == NULL) return -1; return lame_encoder->encode(pBuffer,iDataSize); } __int64 WINAPI irc_encode_flush() { if (lame_encoder == NULL) return -1; return lame_encoder->flush(); } bool WINAPI irc_encode_exit() { if (lame_encoder == NULL) return false; delete lame_encoder; lame_encoder = NULL; return true; } bool WINAPI irc_encode_config() { CConfigDlg ConfigDlg(&encoder_cfg); ConfigDlg.DoModal(); return true; } ================================================ FILE: src/codecs/lame/lame.def ================================================ LIBRARY "lame.irc" EXPORTS irc_capabilities irc_string irc_set_callback irc_decode_init irc_decode_process irc_decode_exit irc_encode_init irc_encode_process irc_encode_flush irc_encode_exit irc_encode_config ================================================ FILE: src/codecs/lame/lame.rc ================================================ // Microsoft Visual C++ generated resource script. // #include "resource.h" #define APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 2 resource. // #include "afxres.h" ///////////////////////////////////////////////////////////////////////////// #undef APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // English (U.S.) resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) #ifdef _WIN32 LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US #pragma code_page(1252) #endif //_WIN32 #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 1 TEXTINCLUDE BEGIN "resource.h\0" END 2 TEXTINCLUDE BEGIN "#include ""afxres.h""\r\n" "\0" END 3 TEXTINCLUDE BEGIN "\r\n" "\0" END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Dialog // IDD_PROPPAGE_CONFIGGENERAL DIALOGEX 0, 0, 214, 156 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "Preset:",IDC_PRESETSTATIC,7,9,24,8 COMBOBOX IDC_PRESETCOMBO,60,7,147,65,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP CONTROL "",IDC_BEVELSTATIC,"Static",SS_ETCHEDHORZ | WS_GROUP,7, 25,200,1,WS_EX_STATICEDGE LTEXT "Encode quality:",IDC_ENCODEQUALITYSTATIC,7,33,50,8 COMBOBOX IDC_ENCODEQUALITYCOMBO,60,31,69,30,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP CONTROL "Mono encoding",IDC_MONOCHECK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,134,32,73,10 CONTROL "",IDC_BEVELSTATIC2,"Static",SS_ETCHEDHORZ | WS_GROUP,7, 48,199,1,WS_EX_STATICEDGE CONTROL "Bitrate mode",IDC_BITRATERADIO,"Button", BS_AUTORADIOBUTTON,7,53,200,10 LTEXT "Bitrate:",IDC_BITRATESTATIC,19,63,35,8 CONTROL "",IDC_BITRATESLIDER,"msctls_trackbar32",TBS_TOOLTIPS | WS_TABSTOP,52,63,155,12 LTEXT "320",IDC_BITRATE320STATIC,195,76,13,8 LTEXT "128",IDC_BITRATE128STATIC,107,76,13,8 LTEXT "192",IDC_BITRATE192STATIC,136,76,13,8 LTEXT "64",IDC_BITRATE64STATIC,80,76,9,8 LTEXT "8",IDC_BITRATE8STATIC,56,76,8,8 CONTROL "Restrict encoder to constant bitrate",IDC_BITRATECHECK, "Button",BS_AUTOCHECKBOX | WS_TABSTOP,56,86,151,10 CONTROL "Quality mode",IDC_QUALITYRADIO,"Button", BS_AUTORADIOBUTTON,7,100,200,10 LTEXT "Quality:",IDC_QUALITYSTATIC,19,110,26,8 CONTROL "",IDC_QUALITYSLIDER,"msctls_trackbar32",TBS_AUTOTICKS | TBS_TOOLTIPS | WS_TABSTOP,52,110,155,12 LTEXT "High",IDC_QUALITYHIGHSTATIC,52,123,15,8 LTEXT "Low",IDC_QUALITYLOWSTATIC,195,123,14,8 LTEXT "VBR mode:",IDC_VBRMODESTATIC,19,136,36,8 COMBOBOX IDC_VBRMODECOMBO,60,135,69,30,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP END ///////////////////////////////////////////////////////////////////////////// // // DESIGNINFO // #ifdef APSTUDIO_INVOKED GUIDELINES DESIGNINFO BEGIN IDD_PROPPAGE_CONFIGGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 207 TOPMARGIN, 7 BOTTOMMARGIN, 147 END END #endif // APSTUDIO_INVOKED #endif // English (U.S.) resources ///////////////////////////////////////////////////////////////////////////// #ifndef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 3 resource. // ///////////////////////////////////////////////////////////////////////////// #endif // not APSTUDIO_INVOKED ================================================ FILE: src/codecs/lame/lame_base.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "lame_base.hh" tirc_send_message *LameBase::send_message_ = NULL; LameBase::LameBase() { // Initialize LAME. lame_gfp_ = lame_init(); // Change error, debug and message handlers. lame_set_errorf(lame_gfp_,handler_errorf); lame_set_debugf(lame_gfp_,handler_debugf); lame_set_msgf(lame_gfp_,handler_msgf); } LameBase::~LameBase() { // Close LAME. lame_close(lame_gfp_); } void LameBase::set_callback(tirc_send_message *callback) { send_message_ = callback; } bool LameBase::send_message(int type,const TCHAR * msg) { if (send_message_ == NULL) return false; send_message_(type,msg); return true; } void LameBase::handler_errorf(const char *format,va_list ap) { // The 64-bit compiler does not support this type of usage of va_start. #ifdef _M_X64 send_message(IRC_MESSAGE_ERROR,_T("Unknown error in lame.irc (x64 build).")); #else va_start(ap,format); int len = _vscprintf(format,ap) + 1; char *msg = new char[len]; vsprintf(msg,format,ap); ckcore::tstring msg_str = ckcore::string::ansi_to_auto<8192>(msg); send_message(IRC_MESSAGE_ERROR,msg_str.c_str()); delete [] msg; #endif } void LameBase::handler_debugf(const char *format,va_list ap) { // Ignore debug messages. } void LameBase::handler_msgf(const char *format,va_list ap) { #ifdef _M_X64 // Ignore information messages. #else va_start(ap,format); int len = _vscprintf(format,ap) + 1; char *msg = new char[len]; vsprintf(msg,format,ap); ckcore::tstring msg_str = ckcore::string::ansi_to_auto<8192>(msg); send_message(IRC_MESSAGE_INFO,msg_str.c_str()); delete [] msg; #endif } ================================================ FILE: src/codecs/lame/lame_base.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include class LameBase { private: static tirc_send_message *send_message_; static void handler_errorf(const char *format,va_list ap); static void handler_debugf(const char *format,va_list ap); static void handler_msgf(const char *format,va_list ap); protected: lame_global_flags *lame_gfp_; static bool send_message(int type,const TCHAR * msg); public: LameBase(); virtual ~LameBase(); static void set_callback(tirc_send_message *callback); }; ================================================ FILE: src/codecs/lame/lame_encoder.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "lame_encoder.hh" LameEncoder::LameEncoder(const TCHAR *file_path, int num_channels,int sample_rate,int bit_rate, CEncoderConfig &encoder_cfg) : file_(file_path), num_channels_(num_channels),sample_rate_(sample_rate),bit_rate_(bit_rate), encoder_cfg_(encoder_cfg) { } bool LameEncoder::initialize() { // Setup format settings. lame_set_num_channels(lame_gfp_,num_channels_); lame_set_in_samplerate(lame_gfp_,sample_rate_); // Configure the encoder. switch (encoder_cfg_.m_iPreset) { case 0: // Custom. { if (encoder_cfg_.m_iEncodeQuality == CONFIG_EQ_FAST) lame_set_quality(lame_gfp_,7); else if (encoder_cfg_.m_iEncodeQuality == CONFIG_EQ_HIGH) lame_set_quality(lame_gfp_,2); if (encoder_cfg_.m_bMono) lame_set_mode(lame_gfp_,MONO); if (encoder_cfg_.m_bBitrateMode) { // Bitrate mode. if (encoder_cfg_.m_bConstantBitrate) { // CBR. lame_set_VBR(lame_gfp_,vbr_off); lame_set_brate(lame_gfp_,encoder_cfg_.m_iBitrate); } else { // ARB. lame_set_VBR(lame_gfp_,vbr_abr); lame_set_VBR_mean_bitrate_kbps(lame_gfp_,encoder_cfg_.m_iBitrate); } } else { // Quality mode. lame_set_VBR(lame_gfp_,encoder_cfg_.m_bFastVBR ? vbr_mtrh : vbr_rh); lame_set_VBR_q(lame_gfp_,encoder_cfg_.m_iQuality); } break; } case 1: // Medium. lame_set_preset(lame_gfp_,MEDIUM); break; case 2: // Standard. lame_set_preset(lame_gfp_,STANDARD); break; case 3: // Extreme. lame_set_preset(lame_gfp_,EXTREME); break; case 4: // Insane. lame_set_preset(lame_gfp_,INSANE); break; } // Initialize parameters. if (lame_init_params(lame_gfp_) < 0) return false; // Resize encode buffer. buffer_.resize(num_channels_ * ((bit_rate_ / sample_rate_) >> 3) * BUFFER_FACTOR); // Open file. return file_.open(ckcore::File::ckOPEN_WRITE); } __int64 LameEncoder::encode(unsigned char *buffer,__int64 data_size) { if (data_size > 0xffffffff) return -1; if (!file_.test()) return -1; unsigned int sample_size = (bit_rate_ / sample_rate_) >> 3; unsigned int num_samples = (static_cast(data_size) / sample_size) / num_channels_; int written = lame_encode_buffer_interleaved(lame_gfp_,reinterpret_cast(buffer), num_samples,buffer_,buffer_.size()); if (written > 0) { if (file_.write(buffer_,written) == -1) return -1; } else if (written < 0) { return -1; } return (__int64)written; } __int64 LameEncoder::flush() { return lame_encode_flush(lame_gfp_,buffer_,buffer_.size()); } ================================================ FILE: src/codecs/lame/lame_encoder.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include #include #include "config_dlg.hh" #include "lame_base.hh" class LameEncoder : public LameBase { private: enum { BUFFER_FACTOR = 4096 }; private: ckcore::File file_; int num_channels_; int sample_rate_; int bit_rate_; ckcore::Buffer buffer_; CEncoderConfig &encoder_cfg_; public: LameEncoder(const TCHAR *file_path, int num_channels,int sample_rate,int bit_rate, CEncoderConfig &encoder_cfg); bool initialize(); __int64 encode(unsigned char *buffer,__int64 data_size); __int64 flush(); }; ================================================ FILE: src/codecs/lame/lame_vc08.vcproj ================================================ ================================================ FILE: src/codecs/lame/lame_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 Template Win32 Template x64 lame {E595EE31-3670-4F99-AAC0-C06B2B5D02E9} lame Win32Proj DynamicLibrary Unicode DynamicLibrary Unicode Application DynamicLibrary Unicode DynamicLibrary Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) .irc .irc .irc .irc Disabled $(ProjectDir)..\..\..\dep\lame\include\;$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;LAME_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 EditAndContinue /NODEFAULTLIB:LIBCMT %(AdditionalOptions) ckcored.lib;%(AdditionalDependencies) lame.def true $(OutDir)lame.pdb Windows MachineX86 X64 Disabled $(ProjectDir)..\..\..\dep\lame\include\;$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;LAME_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 ProgramDatabase /NODEFAULTLIB:LIBCMT %(AdditionalOptions) ckcored.lib;%(AdditionalDependencies) lame.def true $(OutDir)lame.pdb Windows MachineX64 $(ProjectDir)..\..\..\dep\lame\include\;$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;LAME_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) lame.def true Windows true true MachineX86 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs X64 $(ProjectDir)..\..\..\dep\lame\include\;$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;LAME_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase /LTCG %(AdditionalOptions) ckcore.lib;%(AdditionalDependencies) lame.def true Windows true true MachineX64 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh {20536101-3b0e-43ef-94f9-080d595dac57} false {e2dab91a-8248-4625-8a85-2c2c2a390dd8} false ================================================ FILE: src/codecs/lame/lame_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx Source Files Source Files Source Files Source Files Source Files Source Files Source Files Header Files Header Files Header Files Header Files Header Files Header Files Resource Files ================================================ FILE: src/codecs/lame/resource.h ================================================ //{{NO_DEPENDENCIES}} // Microsoft Visual C++ generated include file. // Used by lame.rc // #define IDD_PROPPAGE_CONFIGGENERAL 106 #define IDC_PRESETSTATIC 1001 #define IDC_PRESETCOMBO 1002 #define IDC_BEVELSTATIC 1003 #define IDC_BEVELSTATIC2 1004 #define IDC_ENCODEQUALITYSTATIC 1005 #define IDC_ENCODEQUALITYCOMBO 1006 #define IDC_MONOCHECK 1007 #define IDC_BITRATERADIO 1008 #define IDC_BITRATESTATIC 1009 #define IDC_BITRATESLIDER 1011 #define IDC_BITRATE320STATIC 1012 #define IDC_BITRATE128STATIC 1013 #define IDC_BITRATE192STATIC 1014 #define IDC_BITRATE64STATIC 1015 #define IDC_BITRATE8STATIC 1016 #define IDC_BITRATECHECK 1017 #define IDC_QUALITYRADIO 1018 #define IDC_QUALITYSTATIC 1019 #define IDC_QUALITYSLIDER 1020 #define IDC_QUALITYHIGHSTATIC 1021 #define IDC_QUALITYLOWSTATIC 1022 #define IDC_VBRMODESTATIC 1023 #define IDC_COMBO2 1024 #define IDC_VBRMODECOMBO 1024 // Next default values for new objects // #ifdef APSTUDIO_INVOKED #ifndef APSTUDIO_READONLY_SYMBOLS #define _APS_NEXT_RESOURCE_VALUE 102 #define _APS_NEXT_COMMAND_VALUE 40001 #define _APS_NEXT_CONTROL_VALUE 1025 #define _APS_NEXT_SYMED_VALUE 101 #endif #endif ================================================ FILE: src/codecs/lame/stdafx.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" ================================================ FILE: src/codecs/lame/stdafx.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once // Exclude rarely-used stuff from Windows headers. #define WIN32_LEAN_AND_MEAN #include #include #include #include #include ================================================ FILE: src/codecs/sndfile/library_helper.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "library_helper.hh" CLibraryHelper::CLibraryHelper() { m_hDllInstance = NULL; irc_sf_open = NULL; irc_sf_close = NULL; irc_sf_format_check = NULL; irc_sf_read_raw = NULL; irc_sf_write_raw = NULL; } CLibraryHelper::~CLibraryHelper() { } bool CLibraryHelper::Load(const TCHAR *szFileName) { m_hDllInstance = LoadLibrary(szFileName); if (m_hDllInstance == NULL) return false; irc_sf_open = (tirc_sf_open)GetProcAddress(m_hDllInstance,"sf_open"); if (irc_sf_open == NULL) return false; irc_sf_close = (tirc_sf_close)GetProcAddress(m_hDllInstance,"sf_close"); if (irc_sf_close == NULL) return false; irc_sf_format_check = (tirc_sf_format_check)GetProcAddress(m_hDllInstance,"sf_format_check"); if (irc_sf_format_check == NULL) return false; irc_sf_read_raw = (tirc_sf_read_raw)GetProcAddress(m_hDllInstance,"sf_read_raw"); if (irc_sf_read_raw == NULL) return false; irc_sf_write_raw = (tirc_sf_write_raw)GetProcAddress(m_hDllInstance,"sf_write_raw"); if (irc_sf_write_raw == NULL) return false; return true; } bool CLibraryHelper::Unload() { if (m_hDllInstance != NULL) return false; FreeLibrary(m_hDllInstance); m_hDllInstance = NULL; irc_sf_open = NULL; irc_sf_close = NULL; irc_sf_format_check = NULL; irc_sf_read_raw = NULL; irc_sf_write_raw = NULL; return true; } bool CLibraryHelper::IsLoaded() { return m_hDllInstance != NULL; } ================================================ FILE: src/codecs/sndfile/library_helper.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once typedef SNDFILE *(*tirc_sf_open)(const char *path,int mode,SF_INFO *sfinfo); typedef int (*tirc_sf_close)(SNDFILE *sndfile); typedef int (*tirc_sf_format_check)(const SF_INFO *info); typedef sf_count_t (*tirc_sf_read_raw)(SNDFILE *sndfile,void *ptr,sf_count_t bytes); typedef sf_count_t (*tirc_sf_write_raw)(SNDFILE *sndfile,const void *ptr,sf_count_t bytes); class CLibraryHelper { private: HINSTANCE m_hDllInstance; public: CLibraryHelper(); ~CLibraryHelper(); bool Load(const TCHAR *szFileName); bool Unload(); bool IsLoaded(); tirc_sf_open irc_sf_open; tirc_sf_close irc_sf_close; tirc_sf_format_check irc_sf_format_check; tirc_sf_read_raw irc_sf_read_raw; tirc_sf_write_raw irc_sf_write_raw; }; ================================================ FILE: src/codecs/sndfile/sndfile.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include #include #include "library_helper.hh" tirc_send_message *g_pSendMessage = NULL; // Capability flags. int g_iCapabilities = IRC_HAS_DECODER | IRC_HAS_ENCODER; // Version and about strings. TCHAR *g_szVersion = _T("0.53.0.0"); TCHAR *g_szAbout = _T("InfraRecorder Wave Codec\n\nCopyright 2006-2012 Christian Kindahl.\n\nThis codec is based on the libsndfile library, created\nby Erik de Castro Lopo. More information can be\nfound on the libsndfile website:\nhttp://www.mega-nerd.com/libsndfile/"); TCHAR *g_szEncoder = _T("Wave"); TCHAR *g_szFileExt = _T(".wav"); // Global variables. SNDFILE *g_hInFile = NULL; SNDFILE *g_hOutFile = NULL; unsigned int g_uiDecSampleRate = 0; unsigned int g_uiDecFrameSize = 0; unsigned __int64 g_uiDecCurrentTime = 0; // Library helper (since this codec uses dynamic loading of libsndfile.dll). CLibraryHelper g_LibraryHelper; BOOL APIENTRY DllMain(HANDLE hModule,DWORD ul_reason_for_call,LPVOID lpReserved) { switch (ul_reason_for_call) { case DLL_PROCESS_ATTACH: case DLL_THREAD_ATTACH: // Calculate the full library file name. TCHAR szFileName[MAX_PATH]; ::GetModuleFileName((HMODULE)hModule,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,_T("libsndfile-1.dll")); // Tell the library helper to load the library. g_LibraryHelper.Load(szFileName); break; case DLL_PROCESS_DETACH: case DLL_THREAD_DETACH: // The codec has been detached, unload the libsndfile library. g_LibraryHelper.Unload(); break; } return TRUE; } /* irc_capabilities ---------------- Returns bit information on what operations that are supported by the codec. */ int WINAPI irc_capabilities() { return g_iCapabilities; } TCHAR *WINAPI irc_string(unsigned int uiID) { switch (uiID) { case IRC_STR_VERSION: return g_szVersion; case IRC_STR_ABOUT: return g_szAbout; case IRC_STR_ENCODER: return g_szEncoder; case IRC_STR_FILEEXT: return g_szFileExt; } return NULL; } bool WINAPI irc_set_callback(tirc_send_message *pSendMessage) { if (pSendMessage == NULL) return false; g_pSendMessage = pSendMessage; return true; } bool WINAPI irc_decode_init(const TCHAR *szFileName,int &iNumChannels, int &iSampleRate,int &iBitRate,unsigned __int64 &uiDuration) { if (!g_LibraryHelper.IsLoaded()) return false; std::string ansi_file_name = ckcore::string::auto_to_ansi<8192>(szFileName); SF_INFO sfInfo; g_hInFile = g_LibraryHelper.irc_sf_open(ansi_file_name.c_str(),SFM_READ,&sfInfo); if (g_hInFile == NULL) return false; // Get file information. iNumChannels = sfInfo.channels; iSampleRate = sfInfo.samplerate; switch (sfInfo.format & SF_FORMAT_SUBMASK) { case SF_FORMAT_PCM_S8: case SF_FORMAT_PCM_U8: iBitRate = sfInfo.samplerate << 3; break; case SF_FORMAT_PCM_16: case SF_FORMAT_DWVW_16: iBitRate = sfInfo.samplerate << 4; break; case SF_FORMAT_PCM_24: case SF_FORMAT_DWVW_24: iBitRate = sfInfo.samplerate * 24; break; case SF_FORMAT_PCM_32: case SF_FORMAT_FLOAT: iBitRate = sfInfo.samplerate << 5; break; case SF_FORMAT_DOUBLE: iBitRate = sfInfo.samplerate << 6; break; case SF_FORMAT_G721_32: iBitRate = 32000; break; case SF_FORMAT_G723_24: iBitRate = 24000; break; case SF_FORMAT_G723_40: iBitRate = 40000; break; case SF_FORMAT_DWVW_12: iBitRate = sfInfo.samplerate * 12; break; /*case SF_FORMAT_ULAW: case SF_FORMAT_ALAW: case SF_FORMAT_IMA_ADPCM: case SF_FORMAT_MS_ADPCM: case SF_FORMAT_GSM610: SF_FORMAT_VOX_ADPCM: case SF_FORMAT_DWVW_N: SF_FORMAT_DPCM_8: SF_FORMAT_DPCM_16:*/ default: iBitRate = -1; g_LibraryHelper.irc_sf_close(g_hInFile); g_hInFile = NULL; return false; //break; } // Calculate file duration (in milliseconds). uiDuration = 0; if (sfInfo.samplerate != 0) uiDuration = (sfInfo.frames / sfInfo.samplerate) * 1000; g_uiDecCurrentTime = 0; // We need to remember the samplerate and frame size so we can calculate // the current time when decoding the file. g_uiDecSampleRate = iSampleRate; g_uiDecFrameSize = ((iBitRate / iSampleRate) >> 3) * iNumChannels; return true; } __int64 WINAPI irc_decode_process(unsigned char *pBuffer,__int64 iBufferSize, unsigned __int64 &uiTime) { if (!g_LibraryHelper.IsLoaded()) return -1; if (iBufferSize < 0) return -1; if (g_hInFile == NULL) return -1; __int64 iRead = g_LibraryHelper.irc_sf_read_raw(g_hInFile,pBuffer,iBufferSize); // Current time (in milliseconds). g_uiDecCurrentTime += ((iRead / g_uiDecFrameSize) * 1000) / g_uiDecSampleRate; uiTime = g_uiDecCurrentTime; return iRead; } bool WINAPI irc_decode_exit() { if (!g_LibraryHelper.IsLoaded()) return false; if (g_hInFile == NULL) return false; g_LibraryHelper.irc_sf_close(g_hInFile); g_hInFile = NULL; return true; } bool WINAPI irc_encode_init(const TCHAR *szFileName,int iNumChannels, int iSampleRate,int iBitRate) { if (!g_LibraryHelper.IsLoaded()) return false; SF_INFO sfInfo; sfInfo.channels = iNumChannels; sfInfo.samplerate = iSampleRate; sfInfo.format = SF_FORMAT_WAV; switch (iBitRate / iSampleRate) { case 8: sfInfo.format |= SF_FORMAT_PCM_S8; break; case 16: sfInfo.format |= SF_FORMAT_PCM_16; break; case 24: sfInfo.format |= SF_FORMAT_PCM_24; break; case 32: sfInfo.format |= SF_FORMAT_PCM_32; break; default: return false; } if (!g_LibraryHelper.irc_sf_format_check(&sfInfo)) return false; std::string ansi_file_name = ckcore::string::auto_to_ansi<8192>(szFileName); g_hOutFile = g_LibraryHelper.irc_sf_open(ansi_file_name.c_str(),SFM_WRITE,&sfInfo); return true; } __int64 WINAPI irc_encode_process(unsigned char *pBuffer,__int64 iDataSize) { if (!g_LibraryHelper.IsLoaded()) return -1; if (iDataSize < 0) return -1; if (g_hOutFile == NULL) return -1; return g_LibraryHelper.irc_sf_write_raw(g_hOutFile,pBuffer,iDataSize); } __int64 WINAPI irc_encode_flush() { return 0; } bool WINAPI irc_encode_exit() { if (!g_LibraryHelper.IsLoaded()) return false; if (g_hOutFile == NULL) return false; g_LibraryHelper.irc_sf_close(g_hOutFile); g_hOutFile = NULL; return true; } bool WINAPI irc_encode_config() { return false; } ================================================ FILE: src/codecs/sndfile/sndfile.def ================================================ LIBRARY "sndfile.irc" EXPORTS irc_capabilities irc_string irc_set_callback irc_decode_init irc_decode_process irc_decode_exit irc_encode_init irc_encode_process irc_encode_flush irc_encode_exit irc_encode_config ================================================ FILE: src/codecs/sndfile/sndfile_vc08.vcproj ================================================ ================================================ FILE: src/codecs/sndfile/sndfile_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 sndfile {533889C9-1598-4823-BFA9-7C97FD35D6DF} sndfile Win32Proj DynamicLibrary Unicode DynamicLibrary Unicode DynamicLibrary Unicode DynamicLibrary Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) .irc .irc .irc .irc Disabled $(ProjectDir)..\..\..\dep\libsndfile\include\;$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;SNDFILE_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 EditAndContinue ckcored.lib;%(AdditionalDependencies) sndfile.def true $(OutDir)sndfile.pdb Windows MachineX86 X64 Disabled $(ProjectDir)..\..\..\dep\libsndfile\include\;$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;SNDFILE_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 ProgramDatabase ckcored.lib;%(AdditionalDependencies) sndfile.def true $(OutDir)sndfile.pdb Windows MachineX64 $(ProjectDir)..\..\..\dep\libsndfile\include\;$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;SNDFILE_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) sndfile.def true Windows true true MachineX86 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs X64 $(ProjectDir)..\..\..\dep\libsndfile\include\;$(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;SNDFILE_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) sndfile.def true Windows true true MachineX64 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh {81ea1bb3-2ba0-4600-9081-2d2cb9203466} false ================================================ FILE: src/codecs/sndfile/sndfile_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx Source Files Source Files Source Files Source Files Header Files Header Files ================================================ FILE: src/codecs/sndfile/stdafx.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" ================================================ FILE: src/codecs/sndfile/stdafx.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once // Exclude rarely-used stuff from Windows headers. #define WIN32_LEAN_AND_MEAN #ifndef _T #define _T TEXT #endif #include ================================================ FILE: src/codecs/vorbis/config_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "config_dlg.hh" CConfigDlg::CConfigDlg(CEncoderConfig *pConfig) : CPropertySheetImpl(_T("Configuration"),0,NULL) { m_bCentered = false; m_psh.dwFlags |= PSH_NOAPPLYNOW; m_GeneralPage.SetConfig(pConfig); AddPage(m_GeneralPage); } CConfigDlg::~CConfigDlg() { } LRESULT CConfigDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } bHandled = FALSE; return 0; } ================================================ FILE: src/codecs/vorbis/config_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "config_general_page.hh" class CConfigDlg : public CPropertySheetImpl { private: bool m_bCentered; CConfigGeneralPage m_GeneralPage; public: CConfigDlg(CEncoderConfig *pConfig); ~CConfigDlg(); BEGIN_MSG_MAP(CConfigDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/codecs/vorbis/config_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "config_general_page.hh" #include CConfigGeneralPage::CConfigGeneralPage() { m_pConfig = NULL; } CConfigGeneralPage::~CConfigGeneralPage() { } bool CConfigGeneralPage::SetConfig(CEncoderConfig *pConfig) { if (pConfig == NULL) return false; m_pConfig = pConfig; return true; } bool CConfigGeneralPage::ValidateBitrateValue(int iControl,int &iValue) { TCHAR szBuffer[4]; GetDlgItemText(iControl,szBuffer,4); iValue = _wtoi(szBuffer); return iValue > 47 && iValue < 501; } bool CConfigGeneralPage::OnApply() { // Bitrates. int iValue; if (!ValidateBitrateValue(IDC_BITRATEEDIT,iValue)) { MessageBox(_T("Invalid constant bitrate value. The value must be between 48 and 500 (inclusive)."),_T("Error"),MB_OK | MB_ICONERROR); return false; } m_pConfig->m_iBitrate = iValue; if (!ValidateBitrateValue(IDC_MINBITRATEEDIT,iValue)) { MessageBox(_T("Invalid minimum bitrate value. The value must be between 48 and 500 (inclusive)."),_T("Error"),MB_OK | MB_ICONERROR); return false; } m_pConfig->m_iMinBitrate = iValue; if (!ValidateBitrateValue(IDC_MAXBITRATEEDIT,iValue)) { MessageBox(_T("Invalid maximum bitrate value. The value must be between 48 and 500 (inclusive)."),_T("Error"),MB_OK | MB_ICONERROR); return false; } m_pConfig->m_iMaxBitrate = iValue; if (!ValidateBitrateValue(IDC_AVBITRATEEDIT,iValue)) { MessageBox(_T("Invalid average bitrate value. The value must be between 48 and 500 (inclusive)."),_T("Error"),MB_OK | MB_ICONERROR); return false; } m_pConfig->m_iAvBitrate = iValue; // Mode. if (IsDlgButtonChecked(IDC_QUALITYRADIO)) m_pConfig->m_iMode = CONFIG_MODE_QUALITY; else if (IsDlgButtonChecked(IDC_BITRATERADIO)) m_pConfig->m_iMode = CONFIG_MODE_BITRATE; else if (IsDlgButtonChecked(IDC_VARBITRATERADIO)) m_pConfig->m_iMode = CONFIG_MODE_VARBITRATE; else m_pConfig->m_iMode = CONFIG_MODE_AVBITRATE; // Quality. m_pConfig->m_iQuality = m_QualityTrackBar.GetPos(); return true; } LRESULT CConfigGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Setup the quality slider. m_QualityTrackBar = GetDlgItem(IDC_QUALITYSLIDER); for (unsigned int i = 0; i <= 100; i += 10) m_QualityTrackBar.SetTic(i); m_QualityTrackBar.SetLineSize(10); m_QualityTrackBar.SetPageSize(20); m_QualityTrackBar.SetRange(0,100); m_QualityTrackBar.SetPos(m_pConfig->m_iQuality); // Initialize the edit controls. TCHAR szBuffer[4]; lsprintf(szBuffer,_T("%d"),m_pConfig->m_iBitrate); ::SendMessage(GetDlgItem(IDC_BITRATEEDIT),EM_SETLIMITTEXT,3,0); SetDlgItemText(IDC_BITRATEEDIT,szBuffer); lsprintf(szBuffer,_T("%d"),m_pConfig->m_iMinBitrate); ::SendMessage(GetDlgItem(IDC_MINBITRATEEDIT),EM_SETLIMITTEXT,3,0); SetDlgItemText(IDC_MINBITRATEEDIT,szBuffer); lsprintf(szBuffer,_T("%d"),m_pConfig->m_iMaxBitrate); ::SendMessage(GetDlgItem(IDC_MAXBITRATEEDIT),EM_SETLIMITTEXT,3,0); SetDlgItemText(IDC_MAXBITRATEEDIT,szBuffer); lsprintf(szBuffer,_T("%d"),m_pConfig->m_iAvBitrate); ::SendMessage(GetDlgItem(IDC_AVBITRATEEDIT),EM_SETLIMITTEXT,3,0); SetDlgItemText(IDC_AVBITRATEEDIT,szBuffer); // Select the default mode. switch (m_pConfig->m_iMode) { case CONFIG_MODE_QUALITY: CheckDlgButton(IDC_QUALITYRADIO,BST_CHECKED); break; case CONFIG_MODE_BITRATE: CheckDlgButton(IDC_BITRATERADIO,BST_CHECKED); break; case CONFIG_MODE_VARBITRATE: CheckDlgButton(IDC_VARBITRATERADIO,BST_CHECKED); break; case CONFIG_MODE_AVBITRATE: CheckDlgButton(IDC_AVBITRATERADIO,BST_CHECKED); break; } SelectMode(m_pConfig->m_iMode); return TRUE; } void CConfigGeneralPage::SelectMode(int iMode) { // Quality mode. ::EnableWindow(GetDlgItem(IDC_QUALITYSTATIC),iMode == CONFIG_MODE_QUALITY); ::EnableWindow(GetDlgItem(IDC_QUALITYSLIDER),iMode == CONFIG_MODE_QUALITY); ::EnableWindow(GetDlgItem(IDC_QUALITYHIGHSTATIC),iMode == CONFIG_MODE_QUALITY); ::EnableWindow(GetDlgItem(IDC_QUALITYLOWSTATIC),iMode == CONFIG_MODE_QUALITY); // Constant bitrate mode. ::EnableWindow(GetDlgItem(IDC_BITRATESTATIC),iMode == CONFIG_MODE_BITRATE); ::EnableWindow(GetDlgItem(IDC_BITRATEEDIT),iMode == CONFIG_MODE_BITRATE); ::EnableWindow(GetDlgItem(IDC_BITRATESPIN),iMode == CONFIG_MODE_BITRATE); // Variable bitrate mode. ::EnableWindow(GetDlgItem(IDC_MINBITRATESTATIC),iMode == CONFIG_MODE_VARBITRATE); ::EnableWindow(GetDlgItem(IDC_MINBITRATEEDIT),iMode == CONFIG_MODE_VARBITRATE); ::EnableWindow(GetDlgItem(IDC_MINBITRATESPIN),iMode == CONFIG_MODE_VARBITRATE); ::EnableWindow(GetDlgItem(IDC_MAXBITRATESTATIC),iMode == CONFIG_MODE_VARBITRATE); ::EnableWindow(GetDlgItem(IDC_MAXBITRATEEDIT),iMode == CONFIG_MODE_VARBITRATE); ::EnableWindow(GetDlgItem(IDC_MAXBITRATESPIN),iMode == CONFIG_MODE_VARBITRATE); // Average bitrate mode. ::EnableWindow(GetDlgItem(IDC_AVBITRATESTATIC),iMode == CONFIG_MODE_AVBITRATE); ::EnableWindow(GetDlgItem(IDC_AVBITRATEEDIT),iMode == CONFIG_MODE_AVBITRATE); ::EnableWindow(GetDlgItem(IDC_AVBITRATESPIN),iMode == CONFIG_MODE_AVBITRATE); } LRESULT CConfigGeneralPage::OnQualityCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CheckDlgButton(IDC_BITRATERADIO,BST_UNCHECKED); CheckDlgButton(IDC_VARBITRATERADIO,BST_UNCHECKED); CheckDlgButton(IDC_AVBITRATERADIO,BST_UNCHECKED); SelectMode(CONFIG_MODE_QUALITY); bHandled = false; return TRUE; } LRESULT CConfigGeneralPage::OnBitrateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CheckDlgButton(IDC_QUALITYRADIO,BST_UNCHECKED); CheckDlgButton(IDC_VARBITRATERADIO,BST_UNCHECKED); CheckDlgButton(IDC_AVBITRATERADIO,BST_UNCHECKED); SelectMode(CONFIG_MODE_BITRATE); bHandled = false; return TRUE; } LRESULT CConfigGeneralPage::OnVarBitrateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CheckDlgButton(IDC_QUALITYRADIO,BST_UNCHECKED); CheckDlgButton(IDC_BITRATERADIO,BST_UNCHECKED); CheckDlgButton(IDC_AVBITRATERADIO,BST_UNCHECKED); SelectMode(CONFIG_MODE_VARBITRATE); bHandled = false; return TRUE; } LRESULT CConfigGeneralPage::OnAvBitrateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CheckDlgButton(IDC_QUALITYRADIO,BST_UNCHECKED); CheckDlgButton(IDC_BITRATERADIO,BST_UNCHECKED); CheckDlgButton(IDC_VARBITRATERADIO,BST_UNCHECKED); SelectMode(CONFIG_MODE_AVBITRATE); bHandled = false; return TRUE; } LRESULT CConfigGeneralPage::OnBitrateSpin(int idCtrl,LPNMHDR pNMH,BOOL &bHandled) { NMUPDOWN *lpnmud = (NMUPDOWN *)pNMH; TCHAR szBuffer[4]; // Get the control value. switch (idCtrl) { case IDC_BITRATESPIN: GetDlgItemText(IDC_BITRATEEDIT,szBuffer,4); break; case IDC_MINBITRATESPIN: GetDlgItemText(IDC_MINBITRATEEDIT,szBuffer,4); break; case IDC_MAXBITRATESPIN: GetDlgItemText(IDC_MAXBITRATEEDIT,szBuffer,4); break; case IDC_AVBITRATESPIN: GetDlgItemText(IDC_AVBITRATEEDIT,szBuffer,4); break; } int iValue = _wtoi(szBuffer); // Calculate the new value. if (lpnmud->iDelta < 0) { if (iValue < 48) iValue = 48; else if (iValue < 71) { iValue >>= 3; iValue <<= 3; iValue += 8; } else if (iValue < 175) { iValue >>= 4; iValue <<= 4; iValue += 16; } else { iValue >>= 5; iValue <<= 5; iValue += 32; } if (iValue > 500) iValue = 500; } else { if (iValue > 500) iValue = 500; else if (iValue < 71) { iValue >>= 3; iValue <<= 3; iValue -= 8; } else if (iValue < 175) { iValue >>= 4; iValue <<= 4; iValue -= 16; } else { iValue >>= 5; iValue <<= 5; iValue -= 32; } if (iValue < 48) iValue = 48; } // Set the new value. lsprintf(szBuffer,_T("%d"),iValue); switch (idCtrl) { case IDC_BITRATESPIN: SetDlgItemText(IDC_BITRATEEDIT,szBuffer); break; case IDC_MINBITRATESPIN: SetDlgItemText(IDC_MINBITRATEEDIT,szBuffer); break; case IDC_MAXBITRATESPIN: SetDlgItemText(IDC_MAXBITRATEEDIT,szBuffer); break; case IDC_AVBITRATESPIN: SetDlgItemText(IDC_AVBITRATEEDIT,szBuffer); break; } return TRUE; } ================================================ FILE: src/codecs/vorbis/config_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #define CONFIG_MODE_QUALITY 0 #define CONFIG_MODE_BITRATE 1 #define CONFIG_MODE_VARBITRATE 2 #define CONFIG_MODE_AVBITRATE 3 class CEncoderConfig { public: CEncoderConfig() { m_iMode = CONFIG_MODE_QUALITY; m_iQuality = 50; m_iBitrate = 192; m_iMinBitrate = 128; m_iMaxBitrate = 256; m_iAvBitrate = 192; } int m_iMode; int m_iQuality; int m_iBitrate; int m_iMinBitrate; int m_iMaxBitrate; int m_iAvBitrate; }; class CConfigGeneralPage : public CPropertyPageImpl { private: CTrackBarCtrl m_QualityTrackBar; bool ValidateBitrateValue(int iControl,int &iValue); void SelectMode(int iMode); CEncoderConfig *m_pConfig; public: enum { IDD = IDD_PROPPAGE_CONFIGGENERAL }; CConfigGeneralPage(); ~CConfigGeneralPage(); bool SetConfig(CEncoderConfig *pConfig); bool OnApply(); BEGIN_MSG_MAP(CConfigGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(IDC_QUALITYRADIO,OnQualityCheck) COMMAND_ID_HANDLER(IDC_BITRATERADIO,OnBitrateCheck) COMMAND_ID_HANDLER(IDC_VARBITRATERADIO,OnVarBitrateCheck) COMMAND_ID_HANDLER(IDC_AVBITRATERADIO,OnAvBitrateCheck) NOTIFY_HANDLER(IDC_BITRATESPIN,UDN_DELTAPOS,OnBitrateSpin) NOTIFY_HANDLER(IDC_MINBITRATESPIN,UDN_DELTAPOS,OnBitrateSpin) NOTIFY_HANDLER(IDC_MAXBITRATESPIN,UDN_DELTAPOS,OnBitrateSpin) NOTIFY_HANDLER(IDC_AVBITRATESPIN,UDN_DELTAPOS,OnBitrateSpin) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnQualityCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnBitrateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnVarBitrateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnAvBitrateCheck(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnBitrateSpin(int idCtrl,LPNMHDR pNMH,BOOL &bHandled); }; ================================================ FILE: src/codecs/vorbis/resource.h ================================================ //{{NO_DEPENDENCIES}} // Microsoft Visual C++ generated include file. // Used by irVorbis.rc // #define IDD_PROPPAGE_CONFIGGENERAL 106 #define IDC_BITRATERADIO 1008 #define IDC_BITRATESTATIC 1009 #define IDC_QUALITYRADIO 1018 #define IDC_QUALITYSTATIC 1019 #define IDC_QUALITYSLIDER 1020 #define IDC_QUALITYHIGHSTATIC 1021 #define IDC_QUALITYLOWSTATIC 1022 #define IDC_MINBITRATESPIN 1025 #define IDC_MINBITRATEEDIT 1026 #define IDC_VARBITRATERADIO 1027 #define IDC_AVBITRATERADIO 1028 #define IDC_MINBITRATESTATIC 1029 #define IDC_BITRATESPIN 1030 #define IDC_BITRATEEDIT 1031 #define IDC_MAXBITRATESTATIC 1032 #define IDC_MAXBITRATESPIN 1033 #define IDC_MAXBITRATEEDIT 1034 #define IDC_AVBITRATESTATIC 1035 #define IDC_AVBITRATESPIN 1036 #define IDC_AVBITRATEEDIT 1037 // Next default values for new objects // #ifdef APSTUDIO_INVOKED #ifndef APSTUDIO_READONLY_SYMBOLS #define _APS_NEXT_RESOURCE_VALUE 102 #define _APS_NEXT_COMMAND_VALUE 40001 #define _APS_NEXT_CONTROL_VALUE 1036 #define _APS_NEXT_SYMED_VALUE 101 #endif #endif ================================================ FILE: src/codecs/vorbis/stdafx.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" ================================================ FILE: src/codecs/vorbis/stdafx.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once // Exclude rarely-used stuff from Windows headers. #define WIN32_LEAN_AND_MEAN #include #include #include #include #include ================================================ FILE: src/codecs/vorbis/vorbis.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include #include #include #include #include "config_dlg.hh" #include "vorbis.hh" /*#ifdef _M_X64 #pragma comment(lib,"libogg/win32/Static_Release/ogg_static_x64.lib") #else #pragma comment(lib,"libogg/win32/Static_Release/ogg_static.lib") #endif #pragma comment(lib,"libvorbis/win32/Vorbis_Static_Release/vorbis_static.lib") #pragma comment(lib,"libvorbis/win32/VorbisEnc_Static_Release/vorbisenc_static.lib") #pragma comment(lib,"libvorbis/win32/VorbisFile_Static_Release/vorbisfile_static.lib")*/ tirc_send_message *g_pSendMessage = NULL; // Capability flags. int g_iCapabilities = IRC_HAS_DECODER | IRC_HAS_ENCODER | IRC_HAS_CONFIG; // Version and about strings. TCHAR *g_szVersion = _T("0.53.0.0"); TCHAR *g_szAbout = _T("InfraRecorder Ogg Vorbis Codec\n\nCopyright 2006-2012 Christian Kindahl.\n\nThis codec is using the following 3rd party libraries:\n - libogg: Copyright 2002, Xiph.org Foundation.\n - libvorbis: Copyright 2002-2004 Xiph.org Foundation."); TCHAR *g_szEncoder = _T("Ogg Vorbis"); TCHAR *g_szFileExt = _T(".ogg"); // Global variables. ckcore::File *g_pFile = NULL; FILE *g_hInFile = NULL; int g_iNumChannels = -1; int g_iSampleRate = -1; int g_iBitRate = -1; // Encoding. ogg_page og; ogg_stream_state os; vorbis_dsp_state vd; vorbis_block vb; vorbis_info vi; // Decoding. OggVorbis_File vf; // Encoder configuration. CEncoderConfig g_EncoderConfig; BOOL APIENTRY DllMain(HANDLE hModule,DWORD ul_reason_for_call,LPVOID lpReserved) { return TRUE; } /* irc_capabilities ---------------- Returns bit information on what operations that are supported by the codec. */ int WINAPI irc_capabilities() { return g_iCapabilities; } TCHAR *WINAPI irc_string(unsigned int uiID) { switch (uiID) { case IRC_STR_VERSION: return g_szVersion; case IRC_STR_ABOUT: return g_szAbout; case IRC_STR_ENCODER: return g_szEncoder; case IRC_STR_FILEEXT: return g_szFileExt; } return NULL; } bool WINAPI irc_set_callback(tirc_send_message *pSendMessage) { if (pSendMessage == NULL) return false; g_pSendMessage = pSendMessage; return true; } bool WINAPI irc_decode_init(const TCHAR *szFileName,int &iNumChannels, int &iSampleRate,int &iBitRate,unsigned __int64 &uiDuration) { // Get file handle. g_hInFile = _wfopen(szFileName,_T("rb")); if (g_hInFile == NULL) return false; // Open Vorbis bitstream. if (ov_open(g_hInFile,&vf,NULL,0) < 0) return false; // Throw the comments plus a few lines about the bitstream we're decoding. { char **ppTemp = ov_comment(&vf,-1)->user_comments; vorbis_info *vi = ov_info(&vf,-1); while (*ppTemp) ++ppTemp; iNumChannels = vi->channels; iSampleRate = vi->rate; iBitRate = iSampleRate << 4; } // Get file duration (in milliseconds). uiDuration = (unsigned __int64)ov_time_total(&vf,-1) * 1000; return true; } __int64 WINAPI irc_decode_process(unsigned char *pBuffer,__int64 iBufferSize, unsigned __int64 &uiTime) { static int iCurrentSection; if (iBufferSize > 0xFFFFFFFF) return -1; unsigned long ulRead = ov_read(&vf,(char *)pBuffer,(unsigned int)iBufferSize,0,2,1,&iCurrentSection); if (ulRead < 0) return -1; // Current time (in milliseconds). uiTime = (unsigned __int64)ov_time_tell(&vf) * 1000; return ulRead; } bool WINAPI irc_decode_exit() { // Close the file handle. if (g_hInFile != NULL) { fclose(g_hInFile); g_hInFile = NULL; } // Exit the decoder. ov_clear(&vf); return true; } bool WINAPI irc_encode_init(const TCHAR *szFileName,int iNumChannels, int iSampleRate,int iBitRate) { // Currently we only support a maximum of six channels. if (iNumChannels > 6) return false; if (g_pFile != NULL) return false; g_iNumChannels = iNumChannels; g_iSampleRate = iSampleRate; g_iBitRate = iBitRate; // Open output file. g_pFile = new ckcore::File(szFileName); if (!g_pFile->open(ckcore::File::ckOPEN_WRITE)) { delete g_pFile; g_pFile = NULL; return false; } // Initialize encoder. vorbis_info_init(&vi); // Variable bit rate. /*if (vorbis_encode_init_vbr(&vi,iNumChannels,iSampleRate,0.1f)) return false;*/ // Setup configuration. switch (g_EncoderConfig.m_iMode) { case CONFIG_MODE_QUALITY: if (vorbis_encode_init_vbr(&vi,iNumChannels,iSampleRate, (float)g_EncoderConfig.m_iQuality/100.0f) < 0) return false; break; case CONFIG_MODE_BITRATE: if (vorbis_encode_init(&vi,iNumChannels,iSampleRate,g_EncoderConfig.m_iBitrate * 1000, g_EncoderConfig.m_iBitrate * 1000,g_EncoderConfig.m_iBitrate * 1000) < 0) return false; break; case CONFIG_MODE_VARBITRATE: if (vorbis_encode_init(&vi,iNumChannels,iSampleRate,g_EncoderConfig.m_iMaxBitrate * 1000, -1,g_EncoderConfig.m_iMinBitrate * 1000) < 0) return false; break; case CONFIG_MODE_AVBITRATE: if (vorbis_encode_init(&vi,iNumChannels,iSampleRate,-1, g_EncoderConfig.m_iAvBitrate * 1000,-1) < 0) return false; break; } // Add a comment. vorbis_comment vc; vorbis_comment_init(&vc); vorbis_comment_add_tag(&vc,"ENCODER","irVorbis.irc"); // Set up the analysis state and auxiliary encoding storage. vorbis_analysis_init(&vd,&vi); vorbis_block_init(&vd,&vb); // Pick a random serial number; that way we can more likely build chained streams just by concatenation. srand((int)time(NULL)); ogg_stream_init(&os,rand()); // Write the three header packets. { ogg_packet opHeader; ogg_packet opHeaderComment; ogg_packet opHeaderCode; vorbis_analysis_headerout(&vd,&vc,&opHeader,&opHeaderComment,&opHeaderCode); ogg_stream_packetin(&os,&opHeader); ogg_stream_packetin(&os,&opHeaderComment); ogg_stream_packetin(&os,&opHeaderCode); // This ensures the actual audio data will start on a new page, as per spec. int iResult; while ((iResult = ogg_stream_flush(&os,&og))) { if (iResult == 0) break; g_pFile->write(og.header,og.header_len); g_pFile->write(og.body,og.body_len); } } vorbis_comment_clear(&vc); return true; } /* irc_encode_flush_ex ------------------- Internal function. Flushes the vorbis buffer and writes the output to the file. */ __int64 irc_encode_flush_ex() { __int64 iWritten = 0; // Vorbis does some data preanalysis, then divvies up blocks for // more involved (potentially parallel) processing. Get a single // block for encoding now. ogg_packet op; while (vorbis_analysis_blockout(&vd,&vb) == 1) { // Analysis, assume we want to use bitrate management. vorbis_analysis(&vb,NULL); vorbis_bitrate_addblock(&vb); while (vorbis_bitrate_flushpacket(&vd,&op)) { // Weld the packet into the bitstream. ogg_stream_packetin(&os,&op); // Write out pages (if any). while (true) { if (ogg_stream_pageout(&os,&og) == 0) break; g_pFile->write(og.header,og.header_len); g_pFile->write(og.body,og.body_len); iWritten += og.header_len + og.body_len; // This could be set above, but for illustrative purposes, I do // it here (to show that vorbis does know where the stream ends). if (ogg_page_eos(&og)) return iWritten; } } } return iWritten; } __int64 WINAPI irc_encode_process(unsigned char *pBuffer,__int64 iDataSize) { // The Vorbis encoder can only support 0xFFFFFFFF samples per analysis. if (iDataSize > 0xFFFFFFFF) return -1; // Deinterleave. unsigned int uiSampleSize = (g_iBitRate / g_iSampleRate) >> 3; unsigned int uiNumSamples = ((int)iDataSize / uiSampleSize) / g_iNumChannels; float **ppBuffer = vorbis_analysis_buffer(&vd,uiNumSamples); // The following code is in serious need of optimization. unsigned int uiSampleBitSize = g_iBitRate / g_iSampleRate; float fScaler = (float)((int)1 << (uiSampleBitSize - 1)); switch (g_iNumChannels) { // Three channels. case 3: for (unsigned int i = 0; i < uiNumSamples; i++) { int iTemp1 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 0 * uiSampleSize]); int iTemp2 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 2 * uiSampleSize]); int iTemp3 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 1 * uiSampleSize]); unsigned int uiLastJ = uiSampleSize - 1; unsigned int uiShift = 8; for (unsigned int j = 1; j < uiSampleSize; j++) { if (j != uiLastJ) { iTemp1 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 0 * uiSampleSize + j] << uiShift); iTemp2 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 2 * uiSampleSize + j] << uiShift); iTemp3 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 1 * uiSampleSize + j] << uiShift); } else { iTemp1 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 0 * uiSampleSize + j] << uiShift); iTemp2 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 2 * uiSampleSize + j] << uiShift); iTemp3 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 1 * uiSampleSize + j] << uiShift); } uiShift += 8; } ppBuffer[0][i] = iTemp1/fScaler; ppBuffer[1][i] = iTemp2/fScaler; ppBuffer[2][i] = iTemp3/fScaler; } break; // Five channels. case 5: for (unsigned int i = 0; i < uiNumSamples; i++) { // 6-channels. int iTemp1 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 0 * uiSampleSize]); int iTemp2 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 2 * uiSampleSize]); int iTemp3 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 1 * uiSampleSize]); int iTemp4 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 3 * uiSampleSize]); int iTemp5 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 4 * uiSampleSize]); unsigned int uiLastJ = uiSampleSize - 1; unsigned int uiShift = 8; for (unsigned int j = 1; j < uiSampleSize; j++) { if (j != uiLastJ) { iTemp1 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 0 * uiSampleSize + j] << uiShift); iTemp2 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 2 * uiSampleSize + j] << uiShift); iTemp3 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 1 * uiSampleSize + j] << uiShift); iTemp4 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 3 * uiSampleSize + j] << uiShift); iTemp5 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 4 * uiSampleSize + j] << uiShift); } else { iTemp1 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 0 * uiSampleSize + j] << uiShift); iTemp2 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 2 * uiSampleSize + j] << uiShift); iTemp3 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 1 * uiSampleSize + j] << uiShift); iTemp4 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 3 * uiSampleSize + j] << uiShift); iTemp5 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 4 * uiSampleSize + j] << uiShift); } uiShift += 8; } ppBuffer[0][i] = iTemp1/fScaler; ppBuffer[1][i] = iTemp2/fScaler; ppBuffer[2][i] = iTemp3/fScaler; ppBuffer[3][i] = iTemp4/fScaler; ppBuffer[4][i] = iTemp5/fScaler; } break; // Six channels. case 6: for (unsigned int i = 0; i < uiNumSamples; i++) { // 6-channels. int iTemp1 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 0 * uiSampleSize]); int iTemp2 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 2 * uiSampleSize]); int iTemp3 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 1 * uiSampleSize]); int iTemp4 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 4 * uiSampleSize]); int iTemp5 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 5 * uiSampleSize]); int iTemp6 = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + 3 * uiSampleSize]); unsigned int uiLastJ = uiSampleSize - 1; unsigned int uiShift = 8; for (unsigned int j = 1; j < uiSampleSize; j++) { if (j != uiLastJ) { iTemp1 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 0 * uiSampleSize + j] << uiShift); iTemp2 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 2 * uiSampleSize + j] << uiShift); iTemp3 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 1 * uiSampleSize + j] << uiShift); iTemp4 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 4 * uiSampleSize + j] << uiShift); iTemp5 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 5 * uiSampleSize + j] << uiShift); iTemp6 |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 3 * uiSampleSize + j] << uiShift); } else { iTemp1 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 0 * uiSampleSize + j] << uiShift); iTemp2 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 2 * uiSampleSize + j] << uiShift); iTemp3 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 1 * uiSampleSize + j] << uiShift); iTemp4 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 4 * uiSampleSize + j] << uiShift); iTemp5 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 5 * uiSampleSize + j] << uiShift); iTemp6 |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + 3 * uiSampleSize + j] << uiShift); } uiShift += 8; } ppBuffer[0][i] = iTemp1/fScaler; ppBuffer[1][i] = iTemp2/fScaler; ppBuffer[2][i] = iTemp3/fScaler; ppBuffer[3][i] = iTemp4/fScaler; ppBuffer[4][i] = iTemp5/fScaler; ppBuffer[5][i] = iTemp6/fScaler; } break; // One, two and four channels. case 1: case 2: case 4: for (unsigned int i = 0; i < uiNumSamples; i++) { for (int k = 0; k < g_iNumChannels; k++) { int iTemp = (0xFF & (int)pBuffer[i * (uiSampleSize * g_iNumChannels) + k * uiSampleSize]); unsigned int uiLastJ = uiSampleSize - 1; unsigned int uiShift = 8; for (unsigned int j = 1; j < uiSampleSize; j++) { if (j != uiLastJ) iTemp |= ((unsigned char)pBuffer[i * (uiSampleSize * g_iNumChannels) + k * uiSampleSize + j] << uiShift); else iTemp |= ((signed char)pBuffer[i * (uiSampleSize * g_iNumChannels) + k * uiSampleSize + j] << uiShift); uiShift += 8; } ppBuffer[k][i] = iTemp/fScaler; } } break; default: return -1; } // Tell the library how much we actually submitted. vorbis_analysis_wrote(&vd,uiNumSamples); return irc_encode_flush_ex(); } __int64 WINAPI irc_encode_flush() { vorbis_analysis_wrote(&vd,0); return irc_encode_flush_ex(); } bool WINAPI irc_encode_exit() { // Close the out file. if (g_pFile == NULL) return false; delete g_pFile; g_pFile = NULL; // Destroy the encoder. ogg_stream_clear(&os); vorbis_block_clear(&vb); vorbis_dsp_clear(&vd); vorbis_info_clear(&vi); return true; } bool WINAPI irc_encode_config() { CConfigDlg ConfigDlg(&g_EncoderConfig); ConfigDlg.DoModal(); return true; } ================================================ FILE: src/codecs/vorbis/vorbis.def ================================================ LIBRARY "vorbis.irc" EXPORTS irc_capabilities irc_string irc_set_callback irc_decode_init irc_decode_process irc_decode_exit irc_encode_init irc_encode_process irc_encode_flush irc_encode_exit irc_encode_config ================================================ FILE: src/codecs/vorbis/vorbis.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once /*typedef struct { // Vorbis variables. ogg_page og; ogg_stream_state os; vorbis_dsp_state vd; vorbis_block vb; vorbis_info vi; };*/ ================================================ FILE: src/codecs/vorbis/vorbis.rc ================================================ // Microsoft Visual C++ generated resource script. // #include "resource.h" #define APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 2 resource. // #include "afxres.h" ///////////////////////////////////////////////////////////////////////////// #undef APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // English (U.S.) resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) #ifdef _WIN32 LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US #pragma code_page(1252) #endif //_WIN32 #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 1 TEXTINCLUDE BEGIN "resource.h\0" END 2 TEXTINCLUDE BEGIN "#include ""afxres.h""\r\n" "\0" END 3 TEXTINCLUDE BEGIN "\r\n" "\0" END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Dialog // IDD_PROPPAGE_CONFIGGENERAL DIALOGEX 0, 0, 214, 145 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN CONTROL "Constant bitrate mode",IDC_BITRATERADIO,"Button", BS_AUTORADIOBUTTON,7,41,200,10 CONTROL "Quality mode (recommended)",IDC_QUALITYRADIO,"Button", BS_AUTORADIOBUTTON,7,7,200,10 LTEXT "Quality:",IDC_QUALITYSTATIC,19,17,26,8 CONTROL "",IDC_QUALITYSLIDER,"msctls_trackbar32",TBS_TOOLTIPS | WS_TABSTOP,52,17,155,12 LTEXT "High",IDC_QUALITYHIGHSTATIC,195,30,15,8 LTEXT "Low",IDC_QUALITYLOWSTATIC,52,30,14,8 CONTROL "",IDC_MINBITRATESPIN,"msctls_updown32",UDS_ARROWKEYS, 101,78,11,13 EDITTEXT IDC_MINBITRATEEDIT,61,78,40,13,ES_RIGHT | ES_AUTOHSCROLL CONTROL "Variable bitrate mode",IDC_VARBITRATERADIO,"Button", BS_AUTORADIOBUTTON,7,68,200,10 CONTROL "Average bitrate mode",IDC_AVBITRATERADIO,"Button", BS_AUTORADIOBUTTON,7,112,200,10 LTEXT "Min bitrate:",IDC_MINBITRATESTATIC,19,80,38,8 LTEXT "Bitrate:",IDC_BITRATESTATIC,19,53,25,8 CONTROL "",IDC_BITRATESPIN,"msctls_updown32",UDS_ARROWKEYS,101, 51,11,13 EDITTEXT IDC_BITRATEEDIT,61,51,40,13,ES_RIGHT | ES_AUTOHSCROLL LTEXT "Max bitrate:",IDC_MAXBITRATESTATIC,19,96,40,8 CONTROL "",IDC_MAXBITRATESPIN,"msctls_updown32",UDS_ARROWKEYS, 101,94,11,13 EDITTEXT IDC_MAXBITRATEEDIT,61,94,40,13,ES_RIGHT | ES_AUTOHSCROLL LTEXT "Bitrate:",IDC_AVBITRATESTATIC,19,124,25,8 CONTROL "",IDC_AVBITRATESPIN,"msctls_updown32",UDS_ARROWKEYS,101, 122,11,13 EDITTEXT IDC_AVBITRATEEDIT,61,122,40,13,ES_RIGHT | ES_AUTOHSCROLL END ///////////////////////////////////////////////////////////////////////////// // // DESIGNINFO // #ifdef APSTUDIO_INVOKED GUIDELINES DESIGNINFO BEGIN IDD_PROPPAGE_CONFIGGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 207 TOPMARGIN, 7 BOTTOMMARGIN, 136 END END #endif // APSTUDIO_INVOKED #endif // English (U.S.) resources ///////////////////////////////////////////////////////////////////////////// #ifndef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 3 resource. // ///////////////////////////////////////////////////////////////////////////// #endif // not APSTUDIO_INVOKED ================================================ FILE: src/codecs/vorbis/vorbis_vc08.vcproj ================================================ ================================================ FILE: src/codecs/vorbis/vorbis_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 Template Win32 Template x64 vorbis {571D4215-38A0-42CE-8AB7-DEEE9D2154ED} vorbis Win32Proj DynamicLibrary Unicode DynamicLibrary Unicode Application DynamicLibrary Unicode DynamicLibrary Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) .irc .irc .irc .irc Disabled $(ProjectDir)..\..\;$(ProjectDir)..\..\..\dep\libogg\include\;$(ProjectDir)..\..\..\dep\libvorbis\include\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;VORBIS_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 EditAndContinue /NODEFAULTLIB:LIBCMT %(AdditionalOptions) ckcored.lib;%(AdditionalDependencies) vorbis.def true $(OutDir)vorbis.pdb Windows MachineX86 X64 Disabled $(ProjectDir)..\..\;$(ProjectDir)..\..\..\dep\libogg\include\;$(ProjectDir)..\..\..\dep\libvorbis\include\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;VORBIS_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 ProgramDatabase /NODEFAULTLIB:LIBCMT %(AdditionalOptions) ckcored.lib;%(AdditionalDependencies) vorbis.def true $(OutDir)vorbis.pdb Windows MachineX64 $(ProjectDir)..\..\;$(ProjectDir)..\..\..\dep\libogg\include\;$(ProjectDir)..\..\..\dep\libvorbis\include\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;VORBIS_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) vorbis.def true Windows true true MachineX86 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs X64 $(ProjectDir)..\..\;$(ProjectDir)..\..\..\dep\libogg\include\;$(ProjectDir)..\..\..\dep\libvorbis\include\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;VORBIS_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) vorbis.def true Windows true true MachineX64 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh {15cbfeff-7965-41f5-b4e2-21e8795c9159} false {cebde98b-a6aa-46e6-bc79-faaf823db9ec} false {3a214e06-b95e-4d61-a291-1f8df2ec10fd} false ================================================ FILE: src/codecs/vorbis/vorbis_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx Source Files Source Files Source Files Source Files Source Files Header Files Header Files Header Files Header Files Header Files Resource Files ================================================ FILE: src/codecs/wave/stdafx.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" ================================================ FILE: src/codecs/wave/stdafx.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once // Exclude rarely-used stuff from Windows headers. #define WIN32_LEAN_AND_MEAN #ifndef _T #define _T TEXT #endif #include ================================================ FILE: src/codecs/wave/wave.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "wave_writer.hh" #pragma comment(lib,"vfw32.lib") tirc_send_message *g_pSendMessage = NULL; // Capability flags. int g_iCapabilities = IRC_HAS_DECODER | IRC_HAS_ENCODER; // Version and about strings. TCHAR *g_szVersion = _T("0.53.0.0"); TCHAR *g_szAbout = _T("InfraRecorder Wave Codec\n\nCopyright 2006-2012 Christian Kindahl."); TCHAR *g_szEncoder = _T("Wave"); TCHAR *g_szFileExt = _T(".wav"); // Global variables. PAVIFILE g_pAVIFile = NULL; PAVISTREAM g_pAVIStream = NULL; long g_lCurSample = 0; CWaveWriter g_WaveWriter; BOOL APIENTRY DllMain(HANDLE hModule,DWORD ul_reason_for_call,LPVOID lpReserved) { switch (ul_reason_for_call) { // Initialize COM for the current thread if it hasn't already been initialized. case DLL_PROCESS_ATTACH: case DLL_THREAD_ATTACH: AVIFileInit(); break; case DLL_PROCESS_DETACH: case DLL_THREAD_DETACH: AVIFileExit(); break; }; return TRUE; } /* irc_capabilities ---------------- Returns bit information on what operations that are supported by the codec. */ int WINAPI irc_capabilities() { return g_iCapabilities; } TCHAR *WINAPI irc_string(unsigned int uiID) { switch (uiID) { case IRC_STR_VERSION: return g_szVersion; case IRC_STR_ABOUT: return g_szAbout; case IRC_STR_ENCODER: return g_szEncoder; case IRC_STR_FILEEXT: return g_szFileExt; } return NULL; } bool WINAPI irc_set_callback(tirc_send_message *pSendMessage) { if (pSendMessage == NULL) return false; g_pSendMessage = pSendMessage; return true; } bool WINAPI irc_decode_init(const TCHAR *szFileName,int &iNumChannels, int &iSampleRate,int &iBitRate,unsigned __int64 &uiDuration) { // Open the file. HRESULT hResult = AVIFileOpen(&g_pAVIFile,szFileName,OF_SHARE_DENY_NONE,NULL); if (FAILED(hResult)) return false; // Get the first stream in the file (we assume only one audio stream). hResult = AVIFileGetStream(g_pAVIFile,&g_pAVIStream,streamtypeAUDIO,0); if (FAILED(hResult)) return false; // Gather stream information. long lAudioInfoSize = 0; hResult = AVIStreamFormatSize(g_pAVIStream,0,&lAudioInfoSize); if (FAILED(hResult)) return false; if (lAudioInfoSize < sizeof(WAVEFORMATEX)) lAudioInfoSize = sizeof(WAVEFORMATEX); WAVEFORMATEX *pAudioInfo = (WAVEFORMATEX *)new unsigned char[lAudioInfoSize]; if (pAudioInfo == NULL) return false; hResult = AVIStreamReadFormat(g_pAVIStream,0,pAudioInfo,&lAudioInfoSize); if (FAILED(hResult)) { delete [] pAudioInfo; return false; } if (pAudioInfo->wFormatTag == WAVE_FORMAT_PCM) pAudioInfo->cbSize = 0; iNumChannels = pAudioInfo->nChannels; iSampleRate = pAudioInfo->nSamplesPerSec; iBitRate = iSampleRate * pAudioInfo->wBitsPerSample; // Get stream duration in milliseconds. long lLength = AVIStreamLength(g_pAVIStream); uiDuration = AVIStreamSampleToTime(g_pAVIStream,lLength); g_lCurSample = AVIStreamStart(g_pAVIStream); delete [] pAudioInfo; return true; } __int64 WINAPI irc_decode_process(unsigned char *pBuffer,__int64 iBufferSize, unsigned __int64 &uiTime) { if (iBufferSize > 0x7FFFFFFF) return -1; long lProcessed = 0; long lProcessedSamples = 0; HRESULT hResult = AVIStreamRead(g_pAVIStream,g_lCurSample,AVISTREAMREAD_CONVENIENT, pBuffer,(long)iBufferSize,&lProcessed,&lProcessedSamples); if (FAILED(hResult)) return -1; g_lCurSample += lProcessedSamples; uiTime = AVIStreamSampleToTime(g_pAVIStream,g_lCurSample); return lProcessed; } bool WINAPI irc_decode_exit() { HRESULT hResult = AVIStreamRelease(g_pAVIStream); if (FAILED(hResult)) return false; g_pAVIStream = NULL; hResult = AVIFileRelease(g_pAVIFile); if (FAILED(hResult)) return false; g_pAVIFile = NULL; return true; } bool WINAPI irc_encode_init(const TCHAR *szFileName,int iNumChannels, int iSampleRate,int iBitRate) { return g_WaveWriter.Open(szFileName,iNumChannels,iSampleRate,iBitRate); } __int64 WINAPI irc_encode_process(unsigned char *pBuffer,__int64 iDataSize) { return g_WaveWriter.Write(pBuffer,iDataSize); } __int64 WINAPI irc_encode_flush() { return 0; } bool WINAPI irc_encode_exit() { return g_WaveWriter.Close(); } bool WINAPI irc_encode_config() { return false; } ================================================ FILE: src/codecs/wave/wave.def ================================================ LIBRARY "wave.irc" EXPORTS irc_capabilities irc_string irc_set_callback irc_decode_init irc_decode_process irc_decode_exit irc_encode_init irc_encode_process irc_encode_flush irc_encode_exit irc_encode_config ================================================ FILE: src/codecs/wave/wave_vc08.vcproj ================================================ ================================================ FILE: src/codecs/wave/wave_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 wave {1A7358F8-3F30-4079-8BAB-9399B76B5187} wave Win32Proj DynamicLibrary Unicode true DynamicLibrary Unicode DynamicLibrary Unicode true DynamicLibrary Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) .irc .irc .irc .irc Disabled $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;WAVE_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Level3 EditAndContinue ckcored.lib;%(AdditionalDependencies) wave.def true Windows MachineX86 X64 Disabled $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;WAVE_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Level3 ProgramDatabase ckcored.lib;%(AdditionalDependencies) wave.def true Windows MachineX64 $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;WAVE_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) wave.def true Windows true true MachineX86 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs X64 $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;WAVE_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) wave.def true Windows true true MachineX64 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Use stdafx.hh Use stdafx.hh Use stdafx.hh Use stdafx.hh Use stdafx.hh Use stdafx.hh Use stdafx.hh Use stdafx.hh ================================================ FILE: src/codecs/wave/wave_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav Source Files Source Files Source Files Source Files Header Files Header Files ================================================ FILE: src/codecs/wave/wave_writer.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "wave_writer.hh" CWaveWriter::CWaveWriter() : m_pFile(NULL) { m_iNumChannels = 0; m_iSampleRate = 0; m_iBitRate = 0; m_iBitsPerSample = 0; m_ulNumSamples = 0; } CWaveWriter::~CWaveWriter() { if (m_pFile != NULL) Close(); } bool CWaveWriter::WriteHeader() { if (m_pFile == NULL) return false; unsigned char ucHeader[44]; unsigned long ulBytes = (m_iBitsPerSample + 7) / 8; unsigned long ulDataSize = m_ulNumSamples * ulBytes; // The "RIFF" label. ucHeader[ 0] = 'R'; ucHeader[ 1] = 'I'; ucHeader[ 2] = 'F'; ucHeader[ 3] = 'F'; // Size of the next chunk. unsigned long ulTemp = ulDataSize + (44 - 8) < WAVEWRITER_MAXSIZE ? ulDataSize + (44 - 8) : WAVEWRITER_MAXSIZE; ucHeader[ 4] = (unsigned char)(ulTemp >> 0); ucHeader[ 5] = (unsigned char)(ulTemp >> 8); ucHeader[ 6] = (unsigned char)(ulTemp >> 16); ucHeader[ 7] = (unsigned char)(ulTemp >> 24); // The "WAVE" label. ucHeader[ 8] = 'W'; ucHeader[ 9] = 'A'; ucHeader[10] = 'V'; ucHeader[11] = 'E'; // The "fmt " label. ucHeader[12] = 'f'; ucHeader[13] = 'm'; ucHeader[14] = 't'; ucHeader[15] = ' '; // Length of the PCM declaration (2+2+4+4+2+2). ucHeader[16] = 0x10; ucHeader[17] = 0x00; ucHeader[18] = 0x00; ucHeader[19] = 0x00; // We only support uncompressed linear PCM data. ucHeader[20] = 0x01; ucHeader[21] = 0x00; // Number of channels. ucHeader[22] = (unsigned char)(m_iNumChannels >> 0); ucHeader[23] = (unsigned char)(m_iNumChannels >> 8); // Sample frequency. ulTemp = (unsigned long)(m_iSampleRate + 0.5); ucHeader[24] = (unsigned char)(ulTemp >> 0); ucHeader[25] = (unsigned char)(ulTemp >> 8); ucHeader[26] = (unsigned char)(ulTemp >> 16); ucHeader[27] = (unsigned char)(ulTemp >> 24); // Bytes per second in the data stream. ulTemp *= ulBytes * m_iNumChannels; ucHeader[28] = (unsigned char)(ulTemp >> 0); ucHeader[29] = (unsigned char)(ulTemp >> 8); ucHeader[30] = (unsigned char)(ulTemp >> 16); ucHeader[31] = (unsigned char)(ulTemp >> 24); // Bytes per sample time. ulTemp = ulBytes * m_iNumChannels; ucHeader[32] = (unsigned char)(ulTemp >> 0); ucHeader[33] = (unsigned char)(ulTemp >> 8); // Bits per single sample. ucHeader[34] = (unsigned char)(m_iBitsPerSample >> 0); ucHeader[35] = (unsigned char)(m_iBitsPerSample >> 8); // The "data" label. ucHeader[36] = 'd'; ucHeader[37] = 'a'; ucHeader[38] = 't'; ucHeader[39] = 'a'; // Real length of PCM data ulTemp = ulDataSize < WAVEWRITER_MAXSIZE ? ulDataSize : WAVEWRITER_MAXSIZE; ucHeader[40] = (unsigned char)(ulTemp >> 0); ucHeader[41] = (unsigned char)(ulTemp >> 8); ucHeader[42] = (unsigned char)(ulTemp >> 16); ucHeader[43] = (unsigned char)(ulTemp >> 24); return m_pFile->write(ucHeader,sizeof(ucHeader)) != -1; } bool CWaveWriter::WriteExtensibleHeader() { if (m_pFile == NULL) return false; unsigned char ucHeader[68]; unsigned long ulBytes = (m_iBitsPerSample + 7) / 8; float fDataSize = (float)ulBytes * m_ulNumSamples; // Create the channel mask. unsigned long ulChannelMask; switch (m_iNumChannels) { case 3: ulChannelMask = 7; break; case 4: ulChannelMask = 51; break; case 5: ulChannelMask = 55; break; case 6: ulChannelMask = 63; break; default: ulChannelMask = 0; break; } // The "RIFF" header. ucHeader[0] = 'R'; ucHeader[1] = 'I'; ucHeader[2] = 'F'; ucHeader[3] = 'F'; unsigned long ulTemp = (fDataSize + (68 - 8) < (float)WAVEWRITER_MAXSIZE) ? (unsigned long)fDataSize + (68 - 8) : (unsigned long)WAVEWRITER_MAXSIZE; ucHeader[4] = (unsigned char)(ulTemp >> 0); ucHeader[5] = (unsigned char)(ulTemp >> 8); ucHeader[6] = (unsigned char)(ulTemp >> 16); ucHeader[7] = (unsigned char)(ulTemp >> 24); // The "WAVE" header. ucHeader[8] = 'W'; ucHeader[9] = 'A'; ucHeader[10] = 'V'; ucHeader[11] = 'E'; // The "fmt " header. ucHeader[12] = 'f'; ucHeader[13] = 'm'; ucHeader[14] = 't'; ucHeader[15] = ' '; ucHeader[16] = 0x28; ucHeader[17] = 0x00; ucHeader[18] = 0x00; ucHeader[19] = 0x00; // Extensible format data. ucHeader[20] = 0xFE; ucHeader[21] = 0xFF; ucHeader[22] = (unsigned char)(m_iNumChannels >> 0); ucHeader[23] = (unsigned char)(m_iNumChannels >> 8); ulTemp = (unsigned long)(m_iSampleRate + 0.5); ucHeader[24] = (unsigned char)(ulTemp >> 0); ucHeader[25] = (unsigned char)(ulTemp >> 8); ucHeader[26] = (unsigned char)(ulTemp >> 16); ucHeader[27] = (unsigned char)(ulTemp >> 24); ulTemp = m_iSampleRate * ulBytes * m_iNumChannels; ucHeader[28] = (unsigned char)(ulTemp >> 0); ucHeader[29] = (unsigned char)(ulTemp >> 8); ucHeader[30] = (unsigned char)(ulTemp >> 16); ucHeader[31] = (unsigned char)(ulTemp >> 24); ulTemp = ulBytes * m_iNumChannels; ucHeader[32] = (unsigned char)(ulTemp >> 0); ucHeader[33] = (unsigned char)(ulTemp >> 8); ucHeader[34] = (unsigned char)(m_iBitsPerSample >> 0); ucHeader[35] = (unsigned char)(m_iBitsPerSample >> 8); // cbSize. ucHeader[36] = (unsigned char)(22); ucHeader[37] = (unsigned char)(0); // wValidBitsPerSample. ucHeader[38] = (unsigned char)(m_iBitsPerSample >> 0); ucHeader[39] = (unsigned char)(m_iBitsPerSample >> 8); // dwChannelMask. ulTemp = ulChannelMask; ucHeader[40] = (unsigned char)(ulTemp >> 0); ucHeader[41] = (unsigned char)(ulTemp >> 8); ucHeader[42] = (unsigned char)(ulTemp >> 16); ucHeader[43] = (unsigned char)(ulTemp >> 24); // SubFormat (KSDATAFORMAT_SUBTYPE_PCM: 00000001-0000-0010-8000-00aa00389b71). ucHeader[44] = 0x01; ucHeader[45] = 0x00; ucHeader[46] = 0x00; ucHeader[47] = 0x00; ucHeader[48] = 0x00; ucHeader[49] = 0x00; ucHeader[50] = 0x10; ucHeader[51] = 0x00;ucHeader[52] = 0x80; ucHeader[53] = 0x00; ucHeader[54] = 0x00; ucHeader[55] = 0xaa; ucHeader[56] = 0x00; ucHeader[57] = 0x38; ucHeader[58] = 0x9b; ucHeader[59] = 0x71; // End of extensiable format data. // The "data" label. ucHeader[60] = 'd'; ucHeader[61] = 'a'; ucHeader[62] = 't'; ucHeader[63] = 'a'; ulTemp = fDataSize < WAVEWRITER_MAXSIZE ? (unsigned long)fDataSize : (unsigned long)WAVEWRITER_MAXSIZE; ucHeader[64] = (unsigned char)(ulTemp >> 0); ucHeader[65] = (unsigned char)(ulTemp >> 8); ucHeader[66] = (unsigned char)(ulTemp >> 16); ucHeader[67] = (unsigned char)(ulTemp >> 24); return m_pFile->write(ucHeader,sizeof(ucHeader)) != -1; } bool CWaveWriter::Open(const TCHAR *szFileName,int iNumChannels, int iSampleRate,int iBitRate) { if (m_pFile != NULL) return false; m_pFile = new ckcore::File(szFileName); if (!m_pFile->open(ckcore::File::ckOPEN_WRITE)) { delete m_pFile; m_pFile = NULL; return false; } m_iNumChannels = iNumChannels; m_iSampleRate = iSampleRate; m_iBitRate = iBitRate; m_iBitsPerSample = m_iBitRate / m_iSampleRate; m_ulNumSamples = 0; // Write the wave header. if (m_iNumChannels > 2) WriteExtensibleHeader(); else WriteHeader(); return true; } bool CWaveWriter::Close() { if (m_pFile == NULL) return false; // Re-write the header (contains updated information). m_pFile->seek(0,ckcore::File::ckFILE_BEGIN); if (m_iNumChannels > 2) WriteExtensibleHeader(); else WriteHeader(); delete m_pFile; m_pFile = NULL; return true; } __int64 CWaveWriter::Write(unsigned char *pBuffer,__int64 iDataSize) { if (iDataSize > 0xFFFFFFFF) return -1; int iBytesPerSample = m_iBitsPerSample >> 3; m_ulNumSamples += (unsigned long)iDataSize / iBytesPerSample; return m_pFile->write(pBuffer,(unsigned long)iDataSize); } ================================================ FILE: src/codecs/wave/wave_writer.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #define WAVEWRITER_MAXSIZE 4294967040LU class CWaveWriter { private: ckcore::File *m_pFile; int m_iNumChannels; int m_iSampleRate; int m_iBitRate; int m_iBitsPerSample; unsigned long m_ulNumSamples; bool WriteHeader(); bool WriteExtensibleHeader(); public: CWaveWriter(); ~CWaveWriter(); bool Open(const TCHAR *szFileName,int iNumChannels, int iSampleRate,int iBitRate); bool Close(); __int64 Write(unsigned char *pBuffer,__int64 iDataSize); }; ================================================ FILE: src/codecs/wma/config_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "config_dlg.hh" CConfigDlg::CConfigDlg(CEncoderConfig *pConfig) : CPropertySheetImpl(_T("Configuration"),0,NULL) { m_bCentered = false; m_psh.dwFlags |= PSH_NOAPPLYNOW; m_GeneralPage.SetConfig(pConfig); AddPage(m_GeneralPage); } CConfigDlg::~CConfigDlg() { } LRESULT CConfigDlg::OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the window, once. if (wParam == TRUE && !m_bCentered) { CenterWindow(); m_bCentered = true; } bHandled = FALSE; return 0; } ================================================ FILE: src/codecs/wma/config_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "config_general_page.hh" class CConfigDlg : public CPropertySheetImpl { private: bool m_bCentered; CConfigGeneralPage m_GeneralPage; public: CConfigDlg(CEncoderConfig *pConfig); ~CConfigDlg(); BEGIN_MSG_MAP(CConfigDlg) MESSAGE_HANDLER(WM_SHOWWINDOW,OnShowWindow) CHAIN_MSG_MAP(CPropertySheetImpl) END_MSG_MAP() LRESULT OnShowWindow(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/codecs/wma/config_general_page.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "config_general_page.hh" CConfigGeneralPage::CConfigGeneralPage() { m_pConfig = NULL; } CConfigGeneralPage::~CConfigGeneralPage() { } bool CConfigGeneralPage::SetConfig(CEncoderConfig *pConfig) { if (pConfig == NULL) return false; m_pConfig = pConfig; return true; } bool CConfigGeneralPage::OnApply() { m_pConfig->m_iProfile = (int)m_ProfileList.GetItemData(m_ProfileList.GetCurSel()); return true; } bool CConfigGeneralPage::FillProfileList() { HRESULT hResult = S_OK; IWMProfileManager *pIWMProfileManager = NULL; IWMProfileManager2 *pIWMProfileManager2 = NULL; IWMProfile *pIWMProfile = NULL; TCHAR szProfileName[256]; do { // Create profile manager. hResult = g_LibraryHelper.irc_WMCreateProfileManager(&pIWMProfileManager); if (FAILED(hResult)) break; hResult = pIWMProfileManager->QueryInterface(IID_IWMProfileManager2,(void **)&pIWMProfileManager2); if (FAILED(hResult)) break; // Set system profile version to 8.0. hResult = pIWMProfileManager2->SetSystemProfileVersion(WMT_VER_8_0); if (FAILED(hResult)) break; unsigned long ulNumProfiles = 0; hResult = pIWMProfileManager->GetSystemProfileCount(&ulNumProfiles); if (FAILED(hResult)) break; // Iterate all system profiles. for (unsigned int i = 0; i < ulNumProfiles; i++) { hResult = pIWMProfileManager->LoadSystemProfile(i,&pIWMProfile); if (FAILED(hResult)) break; unsigned long ulProfileNameLen = 255; hResult = pIWMProfile->GetName(szProfileName,&ulProfileNameLen); if (FAILED(hResult)) break; if (!lstrncmp(szProfileName,_T("Windows Media Audio"),19)) { szProfileName[16] = 'W'; szProfileName[17] = 'M'; szProfileName[18] = 'A'; // Add the profile to the list. m_ProfileList.AddString(szProfileName + 16); m_ProfileList.SetItemData(m_ProfileList.GetCount() - 1,i); } if (pIWMProfile != NULL) { pIWMProfile->Release(); pIWMProfile = NULL; } } if (FAILED(hResult)) break; } while (false); // Release all resources. if (pIWMProfile != NULL) { pIWMProfile->Release(); pIWMProfile = NULL; } if (pIWMProfileManager != NULL) { pIWMProfileManager->Release(); pIWMProfileManager = NULL; } if (pIWMProfileManager2 != NULL) { pIWMProfileManager2->Release(); pIWMProfileManager2 = NULL; } if (FAILED(hResult)) return false; // Select the last profile that we found. m_ProfileList.SetCurSel(m_ProfileList.GetCount() - 1); return true; } LRESULT CConfigGeneralPage::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Initialize the profile list. m_ProfileList = GetDlgItem(IDC_PROFILELIST); FillProfileList(); return TRUE; } ================================================ FILE: src/codecs/wma/config_general_page.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include "resource.h" #define CONFIG_PRESET_CUSTOM 0 #define CONFIG_PRESET_MEDIUM 1 #define CONFIG_PRESET_STANDARD 2 #define CONFIG_PRESET_EXTREME 3 #define CONFIG_PRESET_INSANE 4 #define CONFIG_EQ_FAST 0 #define CONFIG_EQ_STANDARD 1 #define CONFIG_EQ_HIGH 2 class CEncoderConfig { public: CEncoderConfig() { // Profile number 21 should hopefully be 128 kbps. m_iProfile = 21; } int m_iProfile; }; class CConfigGeneralPage : public CPropertyPageImpl { private: CListBox m_ProfileList; CEncoderConfig *m_pConfig; bool FillProfileList(); public: enum { IDD = IDD_PROPPAGE_CONFIGGENERAL }; CConfigGeneralPage(); ~CConfigGeneralPage(); bool SetConfig(CEncoderConfig *pConfig); bool OnApply(); BEGIN_MSG_MAP(CConfigGeneralPage) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) CHAIN_MSG_MAP(CPropertyPageImpl) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); }; ================================================ FILE: src/codecs/wma/library_helper.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "library_helper.hh" CLibraryHelper::CLibraryHelper() { m_hDllInstance = NULL; irc_WMCreateProfileManager = NULL; irc_WMCreateWriter = NULL; irc_WMCreateSyncReader = NULL; } CLibraryHelper::~CLibraryHelper() { } bool CLibraryHelper::Load(const TCHAR *szFileName) { m_hDllInstance = LoadLibrary(szFileName); if (m_hDllInstance == NULL) return false; irc_WMCreateProfileManager = (tirc_WMCreateProfileManager)GetProcAddress(m_hDllInstance,"WMCreateProfileManager"); if (irc_WMCreateProfileManager == NULL) return false; irc_WMCreateWriter = (tirc_WMCreateWriter)GetProcAddress(m_hDllInstance,"WMCreateWriter"); if (irc_WMCreateWriter == NULL) return false; irc_WMCreateSyncReader = (tirc_WMCreateSyncReader)GetProcAddress(m_hDllInstance,"WMCreateSyncReader"); if (irc_WMCreateSyncReader == NULL) return false; return true; } bool CLibraryHelper::Unload() { if (m_hDllInstance != NULL) return false; FreeLibrary(m_hDllInstance); m_hDllInstance = NULL; irc_WMCreateProfileManager = NULL; irc_WMCreateWriter = NULL; irc_WMCreateSyncReader = NULL; return true; } bool CLibraryHelper::IsLoaded() { return m_hDllInstance != NULL; } ================================================ FILE: src/codecs/wma/library_helper.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once typedef HRESULT (__stdcall *tirc_WMCreateProfileManager)(IWMProfileManager **ppProfileManager); typedef HRESULT (__stdcall *tirc_WMCreateWriter)(IUnknown *pUnkCert,IWMWriter **ppWriter); typedef HRESULT (__stdcall *tirc_WMCreateSyncReader)(IUnknown *pUnkCert,DWORD dwRights,IWMSyncReader **ppSyncReader); class CLibraryHelper { private: HINSTANCE m_hDllInstance; public: CLibraryHelper(); ~CLibraryHelper(); bool Load(const TCHAR *szFileName); bool Unload(); bool IsLoaded(); tirc_WMCreateProfileManager irc_WMCreateProfileManager; tirc_WMCreateWriter irc_WMCreateWriter; tirc_WMCreateSyncReader irc_WMCreateSyncReader; }; ================================================ FILE: src/codecs/wma/read_stream.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "read_stream.hh" CReadStream::CReadStream() { m_cRefs = 1; m_hFile = INVALID_HANDLE_VALUE; } CReadStream::~CReadStream() { if (m_hFile != INVALID_HANDLE_VALUE) CloseHandle(m_hFile); } // IStream methods. HRESULT CReadStream::Open(const TCHAR *szFileName) { HRESULT hResult = S_OK; m_hFile = CreateFile(szFileName,GENERIC_READ,FILE_SHARE_READ,NULL, OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL); if (m_hFile == INVALID_HANDLE_VALUE) return HRESULT_FROM_WIN32(GetLastError()); if (GetFileType(m_hFile) != FILE_TYPE_DISK) { CloseHandle(m_hFile); m_hFile = INVALID_HANDLE_VALUE; return E_FAIL; } return hResult; } HRESULT CReadStream::Read(void *pv,ULONG cb,ULONG *pcbRead) { if (!ReadFile(m_hFile,pv,cb,pcbRead,NULL)) return HRESULT_FROM_WIN32(GetLastError()); return S_OK; } HRESULT CReadStream::Seek(LARGE_INTEGER dlibMove,DWORD dwOrigin, ULARGE_INTEGER *plibNewPosition) { unsigned long ulMoveMethod; switch (dwOrigin) { case STREAM_SEEK_SET: ulMoveMethod = FILE_BEGIN; break; case STREAM_SEEK_CUR: ulMoveMethod = FILE_CURRENT; break; case STREAM_SEEK_END: ulMoveMethod = FILE_END; break; default: return E_INVALIDARG; }; unsigned long ulPos = SetFilePointer(m_hFile,dlibMove.LowPart,NULL,ulMoveMethod); if (ulPos == 0xFFFFFFFF) return HRESULT_FROM_WIN32(GetLastError()); if (plibNewPosition != NULL) { plibNewPosition->LowPart = ulPos; plibNewPosition->HighPart = 0; } return S_OK; } HRESULT CReadStream::Stat(STATSTG *pstatstg,DWORD grfStatFlag) { if (pstatstg == NULL || grfStatFlag != STATFLAG_NONAME) return E_INVALIDARG; unsigned long ulFileSize = GetFileSize(m_hFile,NULL); if (ulFileSize == 0xFFFFFFFF) return HRESULT_FROM_WIN32(GetLastError()); memset(pstatstg,0,sizeof(STATSTG)); pstatstg->type = STGTY_STREAM; pstatstg->cbSize.LowPart = ulFileSize; return S_OK; } // IStream unimplemented methods. HRESULT STDMETHODCALLTYPE CReadStream::Write(void const *pv,ULONG cb,ULONG *pcbWritten) { return E_NOTIMPL; } HRESULT STDMETHODCALLTYPE CReadStream::SetSize(ULARGE_INTEGER libNewSize) { return E_NOTIMPL; } HRESULT STDMETHODCALLTYPE CReadStream::CopyTo(IStream *pstm,ULARGE_INTEGER cb,ULARGE_INTEGER *pcbRead,ULARGE_INTEGER *pcbWritten) { return E_NOTIMPL; } HRESULT STDMETHODCALLTYPE CReadStream::Commit(DWORD grfCommitFlags) { return E_NOTIMPL; } HRESULT STDMETHODCALLTYPE CReadStream::Revert() { return E_NOTIMPL; } HRESULT STDMETHODCALLTYPE CReadStream::LockRegion(ULARGE_INTEGER libOffset,ULARGE_INTEGER cb,DWORD dwLockType) { return E_NOTIMPL; } HRESULT STDMETHODCALLTYPE CReadStream::UnlockRegion(ULARGE_INTEGER libOffset,ULARGE_INTEGER cb,DWORD dwLockType) { return E_NOTIMPL; } HRESULT STDMETHODCALLTYPE CReadStream::Clone(IStream **ppstm) { return E_NOTIMPL; } // IUnknown methods. HRESULT CReadStream::QueryInterface(REFIID riid,void **ppv) { if (riid == IID_IUnknown || riid == IID_IStream) { *ppv = this; AddRef(); return S_OK; } return E_NOINTERFACE; } ULONG CReadStream::AddRef() { return InterlockedIncrement(&m_cRefs); } ULONG CReadStream::Release() { if (InterlockedDecrement(&m_cRefs) == 0) { delete this; return 0; } return 0xBAD; } ================================================ FILE: src/codecs/wma/read_stream.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include class CReadStream : public IStream { private: HANDLE m_hFile; LONG m_cRefs; public: CReadStream(); ~CReadStream(); HRESULT Open(const TCHAR *szFileName); // IStream methods. HRESULT STDMETHODCALLTYPE Read(void *pv,ULONG cb,ULONG *pcbRead); HRESULT STDMETHODCALLTYPE Seek(LARGE_INTEGER dlibMove,DWORD dwOrigin,ULARGE_INTEGER *plibNewPosition); HRESULT STDMETHODCALLTYPE Stat(STATSTG *pstatstg,DWORD grfStatFlag); HRESULT STDMETHODCALLTYPE Write(void const *pv,ULONG cb,ULONG *pcbWritten); HRESULT STDMETHODCALLTYPE SetSize(ULARGE_INTEGER libNewSize); HRESULT STDMETHODCALLTYPE CopyTo(IStream *pstm,ULARGE_INTEGER cb,ULARGE_INTEGER *pcbRead,ULARGE_INTEGER *pcbWritten); HRESULT STDMETHODCALLTYPE Commit(DWORD grfCommitFlags); HRESULT STDMETHODCALLTYPE Revert(); HRESULT STDMETHODCALLTYPE LockRegion(ULARGE_INTEGER libOffset,ULARGE_INTEGER cb,DWORD dwLockType); HRESULT STDMETHODCALLTYPE UnlockRegion(ULARGE_INTEGER libOffset,ULARGE_INTEGER cb,DWORD dwLockType); HRESULT STDMETHODCALLTYPE Clone(IStream **ppstm); // IUnknown methods. HRESULT STDMETHODCALLTYPE QueryInterface(REFIID riid,void **ppv); ULONG STDMETHODCALLTYPE AddRef(); ULONG STDMETHODCALLTYPE Release(); }; ================================================ FILE: src/codecs/wma/resource.h ================================================ //{{NO_DEPENDENCIES}} // Microsoft Visual C++ generated include file. // Used by irWMA.rc // #define IDD_PROPPAGE_CONFIGGENERAL 106 #define IDC_PROFILESTATIC 1001 #define IDC_LIST1 1002 #define IDC_PROFILELIST 1002 // Next default values for new objects // #ifdef APSTUDIO_INVOKED #ifndef APSTUDIO_READONLY_SYMBOLS #define _APS_NEXT_RESOURCE_VALUE 101 #define _APS_NEXT_COMMAND_VALUE 40001 #define _APS_NEXT_CONTROL_VALUE 1003 #define _APS_NEXT_SYMED_VALUE 101 #endif #endif ================================================ FILE: src/codecs/wma/stdafx.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" // Library helper (since this codec uses dynamic loading of wmvcore.dll). CLibraryHelper g_LibraryHelper; ================================================ FILE: src/codecs/wma/stdafx.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once // Exclude rarely-used stuff from Windows headers. #define WIN32_LEAN_AND_MEAN #include #include #include #include #include #include #include "library_helper.hh" extern CLibraryHelper g_LibraryHelper; ================================================ FILE: src/codecs/wma/wma.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "config_dlg.hh" #include "wma_reader.hh" tirc_send_message *g_pSendMessage = NULL; // Capability flags. int g_iCapabilities = IRC_HAS_DECODER | IRC_HAS_ENCODER | IRC_HAS_CONFIG; // Version and about strings. TCHAR *g_szVersion = _T("0.53.0.0"); TCHAR *g_szAbout = _T("InfraRecorder WMA Codec\n\nCopyright 2006-2012 Christian Kindahl."); TCHAR *g_szEncoder = _T("Windows Media Audio"); TCHAR *g_szFileExt = _T(".wma"); // Global variables. IWMWriter *g_pWMWriter = NULL; IWMProfile *g_pWMProfile = NULL; unsigned __int64 g_uiEncodedData = 0; int g_iBitRate = 0; CWMAReader *g_pWMAReader = NULL; // Encoder configuration. CEncoderConfig g_EncoderConfig; // Is set to true of we should uninitialize COM when we close. bool g_bDeInitializeCOM = false; BOOL APIENTRY DllMain(HANDLE hModule,DWORD ul_reason_for_call,LPVOID lpReserved) { switch (ul_reason_for_call) { // Initialize COM for the current thread if it hasn't already been initialized. case DLL_PROCESS_ATTACH: case DLL_THREAD_ATTACH: if (CoInitialize(NULL) == S_OK) g_bDeInitializeCOM = true; // Tell the library helper to load the WM library. g_LibraryHelper.Load(_T("wmvcore.dll")); break; case DLL_PROCESS_DETACH: case DLL_THREAD_DETACH: if (g_bDeInitializeCOM) CoUninitialize(); // The codec has been detached, unload the libsndfile library. g_LibraryHelper.Unload(); break; }; return TRUE; } bool LocalSendMessage(int iType,const TCHAR *szMessage) { if (g_pSendMessage == NULL) return false; g_pSendMessage(iType,szMessage); return true; } HRESULT LoadSystemProfile(unsigned long ulProfileIndex,IWMProfile **ppIWMProfile) { HRESULT hResult = S_OK; IWMProfileManager *pIWMProfileManager = NULL; IWMProfileManager2 *pIWMProfileManager2 = NULL; if (ppIWMProfile == NULL) return E_POINTER; do { // Create profile manager. hResult = g_LibraryHelper.irc_WMCreateProfileManager(&pIWMProfileManager); if (FAILED(hResult)) break; hResult = pIWMProfileManager->QueryInterface(IID_IWMProfileManager2, (void **)&pIWMProfileManager2); if (FAILED(hResult)) break; // Set system profile version to 8.0. hResult = pIWMProfileManager2->SetSystemProfileVersion(WMT_VER_8_0); if (FAILED(hResult)) break; // Load the system profile by index. hResult = pIWMProfileManager->LoadSystemProfile(ulProfileIndex,ppIWMProfile); if (FAILED(hResult)) break; } while (false); // Release all resources. if (pIWMProfileManager2 != NULL) pIWMProfileManager2->Release(); if (pIWMProfileManager != NULL) pIWMProfileManager->Release(); return hResult; } /* irc_capabilities ---------------- Returns bit information on what operations that are supported by the codec. */ int WINAPI irc_capabilities() { return g_iCapabilities; } TCHAR *WINAPI irc_string(unsigned int uiID) { switch (uiID) { case IRC_STR_VERSION: return g_szVersion; case IRC_STR_ABOUT: return g_szAbout; case IRC_STR_ENCODER: return g_szEncoder; case IRC_STR_FILEEXT: return g_szFileExt; } return NULL; } bool WINAPI irc_set_callback(tirc_send_message *pSendMessage) { if (pSendMessage == NULL) return false; g_pSendMessage = pSendMessage; return true; } bool WINAPI irc_decode_init(const TCHAR *szFileName,int &iNumChannels, int &iSampleRate,int &iBitRate,unsigned __int64 &uiDuration) { if (g_pWMAReader != NULL) return false; if (!g_LibraryHelper.IsLoaded()) return false; // Create the reader. g_pWMAReader = new CWMAReader(); if (!g_pWMAReader->Open(szFileName)) { delete g_pWMAReader; g_pWMAReader = NULL; return false; } // Load media information. IWMOutputMediaProps *pProps = NULL; WM_MEDIA_TYPE *pMediaType = NULL; HRESULT hResult = g_pWMAReader->m_pWMReader->GetOutputProps(0,&pProps); if (FAILED(hResult)) { delete g_pWMAReader; g_pWMAReader = NULL; return false; } // Load media type information. unsigned long ulType = 0; hResult = pProps->GetMediaType(NULL,&ulType); if (FAILED(hResult)) { pProps->Release(); delete g_pWMAReader; g_pWMAReader = NULL; return false; } pMediaType = (WM_MEDIA_TYPE *)new unsigned char[ulType]; if (pMediaType == NULL) { pProps->Release(); delete g_pWMAReader; g_pWMAReader = NULL; return false; } hResult = pProps->GetMediaType(pMediaType,&ulType); if (FAILED(hResult)) { delete [] pMediaType; pProps->Release(); delete g_pWMAReader; g_pWMAReader = NULL; return false; } if (pMediaType->majortype != WMMEDIATYPE_Audio) { delete [] pMediaType; pProps->Release(); delete g_pWMAReader; g_pWMAReader = NULL; return false; } if (pMediaType->formattype != WMFORMAT_WaveFormatEx) { delete [] pMediaType; pProps->Release(); delete g_pWMAReader; g_pWMAReader = NULL; return false; } WAVEFORMATEX *pAudioInfo = (WAVEFORMATEX *)pMediaType->pbFormat; iNumChannels = pAudioInfo->nChannels; iSampleRate = pAudioInfo->nSamplesPerSec; iBitRate = iSampleRate * pAudioInfo->wBitsPerSample; // Clean up. delete [] pMediaType; pProps->Release(); // Load header information. IWMHeaderInfo *pHeaderInfo; hResult = g_pWMAReader->m_pWMReader->QueryInterface(IID_IWMHeaderInfo,(VOID **)&pHeaderInfo); if (FAILED(hResult)) { delete g_pWMAReader; g_pWMAReader = NULL; return false; } unsigned short usStreamNum = 0; unsigned short usLength = 0; unsigned char *pBuffer = NULL; WMT_ATTR_DATATYPE wmtType; // Get value length. hResult = pHeaderInfo->GetAttributeByName(&usStreamNum, g_wszWMDuration,&wmtType,NULL,&usLength); if (FAILED(hResult) && (hResult != ASF_E_NOTFOUND)) { delete g_pWMAReader; g_pWMAReader = NULL; return false; } pBuffer = new unsigned char[usLength]; if (pBuffer == NULL) { delete g_pWMAReader; g_pWMAReader = NULL; return false; } // Get the actual value. hResult = pHeaderInfo->GetAttributeByName(&usStreamNum, g_wszWMDuration,&wmtType,pBuffer,&usLength); uiDuration = *(unsigned __int64 *)pBuffer; uiDuration /= 10000; // The duration should be specified in milliseconds. delete [] pBuffer; return true; } __int64 WINAPI irc_decode_process(unsigned char *pBuffer,__int64 iBufferSize, unsigned __int64 &uiTime) { if (g_pWMAReader == NULL) return false; __int64 iProcessed = 0; unsigned __int64 uiTempTime = 0; HRESULT hResult = g_pWMAReader->DecodeSamples(pBuffer,iBufferSize,iProcessed,uiTempTime); if (FAILED(hResult)) { if (hResult != NS_E_NO_MORE_SAMPLES) return -1; } // Current time (in milliseconds). uiTime = uiTempTime / 10000; return iProcessed; } bool WINAPI irc_decode_exit() { if (g_pWMAReader != NULL) { HRESULT hResult = g_pWMAReader->Close(); delete g_pWMAReader; g_pWMAReader = NULL; } return true; } bool WINAPI irc_encode_init(const TCHAR *szFileName,int iNumChannels, int iSampleRate,int iBitRate) { if (g_pWMWriter != NULL || g_pWMProfile != NULL) return false; if (!g_LibraryHelper.IsLoaded()) return false; // Currently only one configuration of input data is supported. if (iNumChannels != 2 || iSampleRate != 44100 || iBitRate != (iSampleRate << 4)) return false; // Load profile. HRESULT hResult = LoadSystemProfile(g_EncoderConfig.m_iProfile,&g_pWMProfile); if (FAILED(hResult)) { LocalSendMessage(IRC_MESSAGE_ERROR,_T("Failed to load the selected system profile.")); return false; } // Create a WMWriter for the output file and set the profile. hResult = g_LibraryHelper.irc_WMCreateWriter(NULL,&g_pWMWriter); if (FAILED(hResult)) { LocalSendMessage(IRC_MESSAGE_ERROR,_T("Failed to create WMWriter.")); return false; } // Save profile to writer. hResult = g_pWMWriter->SetProfile(g_pWMProfile); if (FAILED(hResult)) { LocalSendMessage(IRC_MESSAGE_ERROR,_T("Failed to set WMWriter profile.")); return false; } // Set output file name. hResult = g_pWMWriter->SetOutputFilename(szFileName); if (FAILED(hResult)) { LocalSendMessage(IRC_MESSAGE_ERROR,_T("Failed to set WMWrite output file name.")); return false; } // Start writing. hResult = g_pWMWriter->BeginWriting(); if (FAILED(hResult)) { if (hResult == NS_E_AUDIO_CODEC_NOT_INSTALLED) LocalSendMessage(IRC_MESSAGE_ERROR,_T("Failed to start the writing process: The required audio codec is not installed.")); else if (hResult == NS_E_INVALID_OUTPUT_FORMAT) LocalSendMessage(IRC_MESSAGE_ERROR,_T("Failed to start the writing process: Invalid output format.")); else if (hResult == NS_E_AUDIO_CODEC_ERROR) LocalSendMessage(IRC_MESSAGE_ERROR,_T("Failed to start the writing process: An unexpected error occurred with the audio codec.")); else LocalSendMessage(IRC_MESSAGE_ERROR,_T("Failed to start the writing process.")); return false; } g_uiEncodedData = 0; g_iBitRate = iBitRate; return true; } __int64 WINAPI irc_encode_process(unsigned char *pBuffer,__int64 iDataSize) { if (iDataSize > 0xFFFFFFFF) return false; if (g_pWMWriter == NULL || g_pWMProfile == NULL) return false; /*HRESULT hResult = WriteSample(pWMWriter,qwSMPTEAvgTimePerFrame,FALSE,dwArbitraryInput, uiRead, ucReadBuffer, iBitRate, iProcessedData ); if (FAILED(hResult)) return -1;*/ HRESULT hResult = S_OK; INSSBuffer *pSample = NULL; unsigned char *pbBuffer = NULL; unsigned long ulBufferSize = 0; hResult = g_pWMWriter->AllocateSample((unsigned long)iDataSize,&pSample); if (FAILED(hResult)) { if (pSample != NULL) pSample->Release(); LocalSendMessage(IRC_MESSAGE_ERROR,_T("Failed to allocate memory for output sample.")); return -1; } hResult = pSample->GetBufferAndLength(&pbBuffer,&ulBufferSize); if (FAILED(hResult)) { if (pSample != NULL) pSample->Release(); return -1; } // This feels stupid. It would be better if I could assign a pointer to the INSSBuffer instead. memcpy(pbBuffer,pBuffer,(int)iDataSize); /*hResult = pSample->SetLength((unsigned long)iDataSize); if (FAILED(hResult)) { if (pSample != NULL) pSample->Release(); return -1; }*/ int iByteRate = g_iBitRate >> 3; unsigned __int64 uiTime = ((g_uiEncodedData * 10000000) / iByteRate) >> 1; // Write the sample to the output stream. hResult = g_pWMWriter->WriteSample(0,uiTime,0,pSample); if (pSample != NULL) pSample->Release(); if (FAILED(hResult)) return -1; g_uiEncodedData += iDataSize; return 0; } __int64 WINAPI irc_encode_flush() { HRESULT hResult = g_pWMWriter->Flush(); if (FAILED(hResult)) return -1; return 0; } bool WINAPI irc_encode_exit() { // Release the writer resources. if (g_pWMWriter != NULL) { HRESULT hResult = g_pWMWriter->EndWriting(); if (FAILED(hResult)) return false; g_pWMWriter->Release(); g_pWMWriter = NULL; } // Release the profile resources. if (g_pWMProfile != NULL) { g_pWMProfile->Release(); g_pWMProfile = NULL; } return true; } bool WINAPI irc_encode_config() { if (!g_LibraryHelper.IsLoaded()) return false; CConfigDlg ConfigDlg(&g_EncoderConfig); ConfigDlg.DoModal(); return true; } ================================================ FILE: src/codecs/wma/wma.def ================================================ LIBRARY "wma.irc" EXPORTS irc_capabilities irc_string irc_set_callback irc_decode_init irc_decode_process irc_decode_exit irc_encode_init irc_encode_process irc_encode_flush irc_encode_exit irc_encode_config ================================================ FILE: src/codecs/wma/wma.rc ================================================ // Microsoft Visual C++ generated resource script. // #include "resource.h" #define APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 2 resource. // #include "afxres.h" ///////////////////////////////////////////////////////////////////////////// #undef APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // English (U.S.) resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) #ifdef _WIN32 LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US #pragma code_page(1252) #endif //_WIN32 #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 1 TEXTINCLUDE BEGIN "resource.h\0" END 2 TEXTINCLUDE BEGIN "#include ""afxres.h""\r\n" "\0" END 3 TEXTINCLUDE BEGIN "\r\n" "\0" END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Dialog // IDD_PROPPAGE_CONFIGGENERAL DIALOGEX 0, 0, 214, 121 STYLE DS_SETFONT | DS_FIXEDSYS | WS_CHILD | WS_DISABLED | WS_CAPTION CAPTION "General" FONT 8, "MS Shell Dlg", 0, 0, 0x0 BEGIN LTEXT "Profile:",IDC_PROFILESTATIC,7,7,24,8 LISTBOX IDC_PROFILELIST,7,18,200,96,LBS_NOINTEGRALHEIGHT | LBS_DISABLENOSCROLL | WS_VSCROLL | WS_TABSTOP END ///////////////////////////////////////////////////////////////////////////// // // DESIGNINFO // #ifdef APSTUDIO_INVOKED GUIDELINES DESIGNINFO BEGIN IDD_PROPPAGE_CONFIGGENERAL, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 207 TOPMARGIN, 7 BOTTOMMARGIN, 114 END END #endif // APSTUDIO_INVOKED #endif // English (U.S.) resources ///////////////////////////////////////////////////////////////////////////// #ifndef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 3 resource. // ///////////////////////////////////////////////////////////////////////////// #endif // not APSTUDIO_INVOKED ================================================ FILE: src/codecs/wma/wma_reader.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "wma_reader.hh" CWMAReader::CWMAReader() { m_pWMReader = NULL; m_pStream = NULL; m_pSample = NULL; m_pSampleBuffer = NULL; m_ulSampleBufferSize = 0; m_ulSampleBufferPos = 0; m_uiCurrentTime = 0; } CWMAReader::~CWMAReader() { if (m_pSample != NULL) { m_pSample->Release(); m_pSample = NULL; } if (m_pWMReader != NULL) { m_pWMReader->Release(); m_pWMReader = NULL; } if (m_pStream != NULL) { delete m_pStream; m_pStream = NULL; } } HRESULT CWMAReader::GetStreamNumber(IWMProfile *pProfile,unsigned short &usStreamNumber) { HRESULT hResult = S_OK; IWMStreamConfig *pStream = NULL; unsigned long ulStreamCount = 0; GUID pguidStreamType; if (pProfile == NULL) return E_INVALIDARG; hResult = pProfile->GetStreamCount(&ulStreamCount); if (FAILED(hResult)) return hResult; usStreamNumber = 0; // Make sure that the file only contains audio streams. for (unsigned long i = 0; i < ulStreamCount; i++) { hResult = pProfile->GetStream(i,&pStream); if (FAILED(hResult)) break; unsigned short usLocalStreamNumber = 0; // Get the stream number of the current stream. hResult = pStream->GetStreamNumber(&usLocalStreamNumber); if (FAILED(hResult)) break; hResult = pStream->GetStreamType(&pguidStreamType); if (FAILED(hResult)) break ; if (pguidStreamType == WMMEDIATYPE_Audio) usStreamNumber = usLocalStreamNumber; if (pStream != NULL) { pStream->Release(); pStream = NULL; } } return hResult; } bool CWMAReader::Open(const TCHAR *szFileName) { if (szFileName == NULL) return false; HRESULT hResult = S_OK; // Create reader. if (m_pWMReader == NULL) { hResult = g_LibraryHelper.irc_WMCreateSyncReader(NULL,0,&m_pWMReader); if (FAILED(hResult)) return false; } // Open file stream. if (m_pStream == NULL) { m_pStream = new CReadStream(); if (m_pStream == NULL) return false; } hResult = m_pStream->Open(szFileName); if (FAILED(hResult)) return false; hResult = m_pWMReader->OpenStream(m_pStream); if (FAILED(hResult)) return false; // Get profile interface. IWMProfile *pProfile = NULL; hResult = m_pWMReader->QueryInterface(IID_IWMProfile,(void **)&pProfile); if (FAILED(hResult)) return false; //return false; // Find out the audio stream number. unsigned short usStreamNumber = 0; hResult = GetStreamNumber(pProfile,usStreamNumber); if (pProfile != NULL) pProfile->Release(); if (FAILED(hResult)) return false; if (usStreamNumber != 0) { WMT_STREAM_SELECTION wmtSS = WMT_ON; hResult = m_pWMReader->SetStreamsSelected(1,&usStreamNumber,&wmtSS); if (FAILED(hResult)) return false; hResult = m_pWMReader->SetReadStreamSamples(usStreamNumber,FALSE); if (FAILED(hResult)) return false; } // Set duration. hResult = m_pWMReader->SetRange(0,0); if (FAILED(hResult)) return false; m_uiCurrentTime = 0; return true; } bool CWMAReader::Close() { if (m_pWMReader != NULL) { HRESULT hResult = m_pWMReader->Close(); if (FAILED(hResult)) return false; m_pWMReader->Release(); m_pWMReader = NULL; } return true; } HRESULT CWMAReader::DecodeSamples(unsigned char *pBuffer,__int64 iBufferSize, __int64 &iProcessed,unsigned __int64 &uiTime) { iProcessed = 0; // If there are any data left in the internal buffer, copy it directly to the // specified buffer. if (m_ulSampleBufferSize > m_ulSampleBufferPos) { unsigned long ulInBuffer = m_ulSampleBufferSize - m_ulSampleBufferPos; if (ulInBuffer > iBufferSize) { memcpy(pBuffer,m_pSampleBuffer + m_ulSampleBufferPos,(int)iBufferSize); m_ulSampleBufferPos += (unsigned long)iBufferSize; iProcessed = iBufferSize; } else { memcpy(pBuffer,m_pSampleBuffer + m_ulSampleBufferPos,ulInBuffer); m_ulSampleBufferSize = 0; m_ulSampleBufferPos = 0; m_pSample->Release(); m_pSample = NULL; iProcessed = ulInBuffer; } uiTime = m_uiCurrentTime; return S_OK; } // Now when the internal buffer is empty, read more samples to the // internal buffer. HRESULT hResult = S_OK; unsigned short usStreamNum = 0; unsigned __int64 uiSampleTime = 0; unsigned __int64 uiDuration = 0; unsigned long ulFlags = 0; unsigned long ulOutputNum = 0; hResult = m_pWMReader->GetNextSample(0,&m_pSample,&uiSampleTime,&uiDuration, &ulFlags,&ulOutputNum,&usStreamNum); if (FAILED(hResult)) return hResult; // Buffer management. hResult = m_pSample->GetBufferAndLength(&m_pSampleBuffer,&m_ulSampleBufferSize); if (FAILED(hResult)) return hResult; if (m_ulSampleBufferSize > iBufferSize) { memcpy(pBuffer,m_pSampleBuffer,(int)iBufferSize); m_ulSampleBufferPos += (unsigned long)iBufferSize; iProcessed = iBufferSize; } else { memcpy(pBuffer,m_pSampleBuffer,m_ulSampleBufferSize); iProcessed = m_ulSampleBufferSize; m_ulSampleBufferSize = 0; m_pSample->Release(); m_pSample = NULL; } // Update the internal time variable. m_uiCurrentTime = uiSampleTime; uiTime = m_uiCurrentTime; return hResult; } ================================================ FILE: src/codecs/wma/wma_reader.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "read_stream.hh" class CWMAReader { private: CReadStream *m_pStream; INSSBuffer *m_pSample; unsigned char *m_pSampleBuffer; unsigned long m_ulSampleBufferSize; unsigned long m_ulSampleBufferPos; unsigned __int64 m_uiCurrentTime; HRESULT GetStreamNumber(IWMProfile *pProfile,unsigned short &usStreamNumber); public: IWMSyncReader *m_pWMReader; CWMAReader(); ~CWMAReader(); bool Open(const TCHAR *szFileName); bool Close(); HRESULT DecodeSamples(unsigned char *pBuffer,__int64 iBufferSize, __int64 &iProcessed,unsigned __int64 &uiTime); }; ================================================ FILE: src/codecs/wma/wma_vc08.vcproj ================================================ ================================================ FILE: src/codecs/wma/wma_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 wma {DA677405-57CD-4E24-AC27-4250A4BF0D1C} wma Win32Proj DynamicLibrary Unicode DynamicLibrary Unicode DynamicLibrary Unicode DynamicLibrary Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\codecs\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) .irc .irc .irc .irc Disabled $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;WMA_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 EditAndContinue wma.def true $(OutDir)wma.pdb Windows MachineX86 X64 Disabled $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;WMA_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 ProgramDatabase wma.def true $(OutDir)wma.pdb Windows MachineX64 $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;WMA_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase wma.def true Windows true true MachineX86 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs X64 $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;WMA_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase wma.def true Windows true true MachineX64 copy $(TargetPath) $(ProjectDir)..\..\..\bin\$(Platform)\releasep\codecs stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh ================================================ FILE: src/codecs/wma/wma_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx Source Files Source Files Source Files Source Files Source Files Source Files Source Files Source Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Resource Files ================================================ FILE: src/infrarecorder_vc08.sln ================================================ Microsoft Visual Studio Solution File, Format Version 9.00 # Visual Studio 2005 Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "infrarecorder", "app\infrarecorder_vc08.vcproj", "{949B73FF-BD75-47C0-B965-328513C481B4}" ProjectSection(ProjectDependencies) = postProject {81EA1BB3-2BA0-4600-9081-2D2CB9203466} = {81EA1BB3-2BA0-4600-9081-2D2CB9203466} EndProjectSection EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shell", "shell\shell_vc08.vcproj", "{A6B8E42F-4793-4995-9D63-2906375407AD}" ProjectSection(ProjectDependencies) = postProject {81EA1BB3-2BA0-4600-9081-2D2CB9203466} = {81EA1BB3-2BA0-4600-9081-2D2CB9203466} EndProjectSection EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "base", "base\base_vc08.vcproj", "{81EA1BB3-2BA0-4600-9081-2D2CB9203466}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "codectester", "tools\codectester\codectester_vc08.vcproj", "{662C79E3-70D3-4F83-BAAF-EC663B93BAFD}" ProjectSection(ProjectDependencies) = postProject {81EA1BB3-2BA0-4600-9081-2D2CB9203466} = {81EA1BB3-2BA0-4600-9081-2D2CB9203466} EndProjectSection EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "tools", "tools", "{2C836544-04C4-4839-AAF0-CE9526E167F6}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "main", "main", "{8D08569A-D3CE-4690-A244-AA1704ED3147}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "translationtool", "tools\translationtool\translationtool_vc08.vcproj", "{890C6C24-55F8-466B-91BE-221F6214C3B8}" ProjectSection(ProjectDependencies) = postProject {81EA1BB3-2BA0-4600-9081-2D2CB9203466} = {81EA1BB3-2BA0-4600-9081-2D2CB9203466} EndProjectSection EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "lame", "codecs\lame\lame_vc08.vcproj", "{E595EE31-3670-4F99-AAC0-C06B2B5D02E9}" ProjectSection(ProjectDependencies) = postProject {4B152319-0AF6-4E1B-A284-805D6483C5F1} = {4B152319-0AF6-4E1B-A284-805D6483C5F1} {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4} = {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4} EndProjectSection EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "codecs", "codecs", "{B13D61CA-7A76-4A61-A488-2F8D06DAF06C}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libmp3lame_vc8", "..\dep\lame\libmp3lame\libmp3lame_vc8.vcproj", "{4B152319-0AF6-4E1B-A284-805D6483C5F1}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "dependencies", "dependencies", "{342929BB-3FEE-47E9-A6ED-C391DE6A018D}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "mpglib_vc8", "..\dep\lame\mpglib\mpglib_vc8.vcproj", "{0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "sndfile", "codecs\sndfile\sndfile_vc08.vcproj", "{533889C9-1598-4823-BFA9-7C97FD35D6DF}" ProjectSection(ProjectDependencies) = postProject {81EA1BB3-2BA0-4600-9081-2D2CB9203466} = {81EA1BB3-2BA0-4600-9081-2D2CB9203466} EndProjectSection EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "wave", "codecs\wave\wave_vc08.vcproj", "{1A7358F8-3F30-4079-8BAB-9399B76B5187}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "wma", "codecs\wma\wma_vc08.vcproj", "{DA677405-57CD-4E24-AC27-4250A4BF0D1C}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "vorbis", "codecs\vorbis\vorbis_vc08.vcproj", "{571D4215-38A0-42CE-8AB7-DEEE9D2154ED}" ProjectSection(ProjectDependencies) = postProject {3A214E06-B95E-4D61-A291-1F8DF2EC10FD} = {3A214E06-B95E-4D61-A291-1F8DF2EC10FD} {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC} = {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC} {15CBFEFF-7965-41F5-B4E2-21E8795C9159} = {15CBFEFF-7965-41F5-B4E2-21E8795C9159} EndProjectSection EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libogg_static", "..\dep\libogg\win32\VS2005\libogg_static.vcproj", "{15CBFEFF-7965-41F5-B4E2-21E8795C9159}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libvorbis_static", "..\dep\libvorbis\win32\VS2005\libvorbis\libvorbis_static.vcproj", "{3A214E06-B95E-4D61-A291-1F8DF2EC10FD}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libvorbisfile", "..\dep\libvorbis\win32\VS2005\libvorbisfile\libvorbisfile_static.vcproj", "{CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "setup", "setup", "{4A43E150-27F3-4779-B894-9D5471CB90F9}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ir_plugin", "setup\ir_plugin\ir_plugin_vc08.vcproj", "{BC845F0A-9F4D-4A2F-8366-30B816498DBD}" ProjectSection(ProjectDependencies) = postProject {81EA1BB3-2BA0-4600-9081-2D2CB9203466} = {81EA1BB3-2BA0-4600-9081-2D2CB9203466} EndProjectSection EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "setup_nsis", "setup\setup_nsis_vc08.vcproj", "{B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}" ProjectSection(ProjectDependencies) = postProject {DA677405-57CD-4E24-AC27-4250A4BF0D1C} = {DA677405-57CD-4E24-AC27-4250A4BF0D1C} {BC845F0A-9F4D-4A2F-8366-30B816498DBD} = {BC845F0A-9F4D-4A2F-8366-30B816498DBD} {571D4215-38A0-42CE-8AB7-DEEE9D2154ED} = {571D4215-38A0-42CE-8AB7-DEEE9D2154ED} {A6B8E42F-4793-4995-9D63-2906375407AD} = {A6B8E42F-4793-4995-9D63-2906375407AD} {44E47ABA-9695-4A96-BC52-53585C6AAA3C} = {44E47ABA-9695-4A96-BC52-53585C6AAA3C} {533889C9-1598-4823-BFA9-7C97FD35D6DF} = {533889C9-1598-4823-BFA9-7C97FD35D6DF} {949B73FF-BD75-47C0-B965-328513C481B4} = {949B73FF-BD75-47C0-B965-328513C481B4} EndProjectSection EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "setup_wix", "setup\setup_wix_vc08.vcproj", "{295627F8-6235-4E9D-992F-F200A7F40173}" ProjectSection(ProjectDependencies) = postProject {949B73FF-BD75-47C0-B965-328513C481B4} = {949B73FF-BD75-47C0-B965-328513C481B4} {1A7358F8-3F30-4079-8BAB-9399B76B5187} = {1A7358F8-3F30-4079-8BAB-9399B76B5187} {44E47ABA-9695-4A96-BC52-53585C6AAA3C} = {44E47ABA-9695-4A96-BC52-53585C6AAA3C} {A6B8E42F-4793-4995-9D63-2906375407AD} = {A6B8E42F-4793-4995-9D63-2906375407AD} {DA677405-57CD-4E24-AC27-4250A4BF0D1C} = {DA677405-57CD-4E24-AC27-4250A4BF0D1C} EndProjectSection EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "help", "help", "{176EBD88-B63B-466F-BB4F-3C331C89BF24}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "help_english", "..\doc\english\help_english_vc08.vcproj", "{44E47ABA-9695-4A96-BC52-53585C6AAA3C}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "tests", "tests", "{5B05DB5E-5941-4418-A8D1-37101F2A8E07}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tests", "tests\tests_vc08.vcproj", "{2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}" ProjectSection(ProjectDependencies) = postProject {81EA1BB3-2BA0-4600-9081-2D2CB9203466} = {81EA1BB3-2BA0-4600-9081-2D2CB9203466} EndProjectSection EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Win32 = Debug|Win32 Debug|x64 = Debug|x64 Release|Win32 = Release|Win32 Release|x64 = Release|x64 ReleaseP|Win32 = ReleaseP|Win32 ReleaseP|x64 = ReleaseP|x64 EndGlobalSection GlobalSection(ProjectConfigurationPlatforms) = postSolution {949B73FF-BD75-47C0-B965-328513C481B4}.Debug|Win32.ActiveCfg = Debug|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.Debug|Win32.Build.0 = Debug|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.Debug|x64.ActiveCfg = Debug|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.Debug|x64.Build.0 = Debug|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.Release|Win32.ActiveCfg = Release|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.Release|Win32.Build.0 = Release|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.Release|x64.ActiveCfg = Release|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.Release|x64.Build.0 = Release|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.ReleaseP|Win32.ActiveCfg = ReleaseP|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.ReleaseP|Win32.Build.0 = ReleaseP|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.ReleaseP|x64.ActiveCfg = ReleaseP|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.ReleaseP|x64.Build.0 = ReleaseP|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.Debug|Win32.ActiveCfg = Debug|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.Debug|Win32.Build.0 = Debug|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.Debug|x64.ActiveCfg = Debug|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.Debug|x64.Build.0 = Debug|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.Release|Win32.ActiveCfg = Release|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.Release|Win32.Build.0 = Release|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.Release|x64.ActiveCfg = Release|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.Release|x64.Build.0 = Release|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.ReleaseP|Win32.ActiveCfg = ReleaseP|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.ReleaseP|Win32.Build.0 = ReleaseP|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.ReleaseP|x64.ActiveCfg = ReleaseP|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.ReleaseP|x64.Build.0 = ReleaseP|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Debug|Win32.ActiveCfg = Debug|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Debug|Win32.Build.0 = Debug|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Debug|x64.ActiveCfg = Debug|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Debug|x64.Build.0 = Debug|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Release|Win32.ActiveCfg = Release|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Release|Win32.Build.0 = Release|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Release|x64.ActiveCfg = Release|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Release|x64.Build.0 = Release|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.ReleaseP|Win32.ActiveCfg = Release|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.ReleaseP|Win32.Build.0 = Release|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.ReleaseP|x64.ActiveCfg = Release|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.ReleaseP|x64.Build.0 = Release|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Debug|Win32.ActiveCfg = Debug|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Debug|Win32.Build.0 = Debug|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Debug|x64.ActiveCfg = Debug|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Debug|x64.Build.0 = Debug|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Release|Win32.ActiveCfg = Release|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Release|Win32.Build.0 = Release|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Release|x64.ActiveCfg = Release|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Release|x64.Build.0 = Release|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.ReleaseP|Win32.ActiveCfg = Release|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.ReleaseP|x64.ActiveCfg = Release|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Debug|Win32.ActiveCfg = Debug|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Debug|Win32.Build.0 = Debug|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Debug|x64.ActiveCfg = Debug|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Debug|x64.Build.0 = Debug|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Release|Win32.ActiveCfg = Release|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Release|Win32.Build.0 = Release|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Release|x64.ActiveCfg = Release|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Release|x64.Build.0 = Release|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.ReleaseP|Win32.ActiveCfg = Release|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.ReleaseP|x64.ActiveCfg = Release|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Debug|Win32.ActiveCfg = Debug|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Debug|Win32.Build.0 = Debug|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Debug|x64.ActiveCfg = Debug|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Debug|x64.Build.0 = Debug|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Release|Win32.ActiveCfg = Release|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Release|Win32.Build.0 = Release|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Release|x64.ActiveCfg = Release|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Release|x64.Build.0 = Release|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.ReleaseP|Win32.ActiveCfg = Release|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.ReleaseP|Win32.Build.0 = Release|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.ReleaseP|x64.ActiveCfg = Release|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.ReleaseP|x64.Build.0 = Release|x64 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.Debug|Win32.ActiveCfg = Debug|Win32 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.Debug|Win32.Build.0 = Debug|Win32 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.Debug|x64.ActiveCfg = Debug|x64 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.Debug|x64.Build.0 = Debug|x64 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.Release|Win32.ActiveCfg = Release|Win32 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.Release|Win32.Build.0 = Release|Win32 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.Release|x64.ActiveCfg = Release|x64 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.Release|x64.Build.0 = Release|x64 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.ReleaseP|Win32.ActiveCfg = Release|Win32 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.ReleaseP|Win32.Build.0 = Release|Win32 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.ReleaseP|x64.ActiveCfg = Release|x64 {4B152319-0AF6-4E1B-A284-805D6483C5F1}.ReleaseP|x64.Build.0 = Release|x64 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.Debug|Win32.ActiveCfg = Debug|Win32 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.Debug|Win32.Build.0 = Debug|Win32 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.Debug|x64.ActiveCfg = Debug|x64 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.Debug|x64.Build.0 = Debug|x64 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.Release|Win32.ActiveCfg = Release|Win32 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.Release|Win32.Build.0 = Release|Win32 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.Release|x64.ActiveCfg = Release|x64 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.Release|x64.Build.0 = Release|x64 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.ReleaseP|Win32.ActiveCfg = Release|Win32 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.ReleaseP|Win32.Build.0 = Release|Win32 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.ReleaseP|x64.ActiveCfg = Release|x64 {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4}.ReleaseP|x64.Build.0 = Release|x64 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Debug|Win32.ActiveCfg = Debug|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Debug|Win32.Build.0 = Debug|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Debug|x64.ActiveCfg = Debug|x64 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Debug|x64.Build.0 = Debug|x64 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Release|Win32.ActiveCfg = Release|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Release|Win32.Build.0 = Release|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Release|x64.ActiveCfg = Release|x64 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Release|x64.Build.0 = Release|x64 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.ReleaseP|Win32.ActiveCfg = Release|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.ReleaseP|Win32.Build.0 = Release|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.ReleaseP|x64.ActiveCfg = Release|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Debug|Win32.ActiveCfg = Debug|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Debug|Win32.Build.0 = Debug|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Debug|x64.ActiveCfg = Debug|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Debug|x64.Build.0 = Debug|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Release|Win32.ActiveCfg = Release|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Release|Win32.Build.0 = Release|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Release|x64.ActiveCfg = Release|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Release|x64.Build.0 = Release|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.ReleaseP|Win32.ActiveCfg = Release|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.ReleaseP|x64.ActiveCfg = Release|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.ReleaseP|x64.Build.0 = Release|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Debug|Win32.ActiveCfg = Debug|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Debug|Win32.Build.0 = Debug|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Debug|x64.ActiveCfg = Debug|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Debug|x64.Build.0 = Debug|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Release|Win32.ActiveCfg = Release|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Release|Win32.Build.0 = Release|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Release|x64.ActiveCfg = Release|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Release|x64.Build.0 = Release|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.ReleaseP|Win32.ActiveCfg = Release|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.ReleaseP|Win32.Build.0 = Release|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.ReleaseP|x64.ActiveCfg = Release|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.ReleaseP|x64.Build.0 = Release|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Debug|Win32.ActiveCfg = Debug|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Debug|Win32.Build.0 = Debug|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Debug|x64.ActiveCfg = Debug|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Debug|x64.Build.0 = Debug|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Release|Win32.ActiveCfg = Release|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Release|Win32.Build.0 = Release|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Release|x64.ActiveCfg = Release|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Release|x64.Build.0 = Release|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.ReleaseP|Win32.ActiveCfg = Release|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.ReleaseP|Win32.Build.0 = Release|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.ReleaseP|x64.ActiveCfg = Release|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.ReleaseP|x64.Build.0 = Release|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Debug|Win32.ActiveCfg = Debug|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Debug|Win32.Build.0 = Debug|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Debug|x64.ActiveCfg = Debug|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Debug|x64.Build.0 = Debug|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Release|Win32.ActiveCfg = Release|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Release|Win32.Build.0 = Release|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Release|x64.ActiveCfg = Release|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Release|x64.Build.0 = Release|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.ReleaseP|Win32.ActiveCfg = Release|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.ReleaseP|Win32.Build.0 = Release|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.ReleaseP|x64.ActiveCfg = Release|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.ReleaseP|x64.Build.0 = Release|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Debug|Win32.ActiveCfg = Debug|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Debug|Win32.Build.0 = Debug|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Debug|x64.ActiveCfg = Debug|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Debug|x64.Build.0 = Debug|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Release|Win32.ActiveCfg = Release|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Release|Win32.Build.0 = Release|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Release|x64.ActiveCfg = Release|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Release|x64.Build.0 = Release|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.ReleaseP|Win32.ActiveCfg = Release|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.ReleaseP|Win32.Build.0 = Release|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.ReleaseP|x64.ActiveCfg = Release|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.ReleaseP|x64.Build.0 = Release|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Debug|Win32.ActiveCfg = Debug|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Debug|Win32.Build.0 = Debug|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Debug|x64.ActiveCfg = Debug|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Debug|x64.Build.0 = Debug|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Release|Win32.ActiveCfg = Release|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Release|Win32.Build.0 = Release|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Release|x64.ActiveCfg = Release|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Release|x64.Build.0 = Release|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.ReleaseP|Win32.ActiveCfg = Release|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.ReleaseP|Win32.Build.0 = Release|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.ReleaseP|x64.ActiveCfg = Release|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.ReleaseP|x64.Build.0 = Release|x64 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Debug|Win32.ActiveCfg = Debug|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Debug|Win32.Build.0 = Debug|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Debug|x64.ActiveCfg = Debug|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Release|Win32.ActiveCfg = Release|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Release|Win32.Build.0 = Release|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Release|x64.ActiveCfg = Release|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.ReleaseP|Win32.ActiveCfg = Release|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.ReleaseP|x64.ActiveCfg = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Debug|Win32.ActiveCfg = Debug|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Debug|x64.ActiveCfg = Debug|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Release|Win32.ActiveCfg = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Release|Win32.Build.0 = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Release|x64.ActiveCfg = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.ReleaseP|Win32.ActiveCfg = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.ReleaseP|x64.ActiveCfg = Release|Win32 {295627F8-6235-4E9D-992F-F200A7F40173}.Debug|Win32.ActiveCfg = Debug|Win32 {295627F8-6235-4E9D-992F-F200A7F40173}.Debug|x64.ActiveCfg = Debug|x64 {295627F8-6235-4E9D-992F-F200A7F40173}.Release|Win32.ActiveCfg = Release|Win32 {295627F8-6235-4E9D-992F-F200A7F40173}.Release|x64.ActiveCfg = Release|x64 {295627F8-6235-4E9D-992F-F200A7F40173}.Release|x64.Build.0 = Release|x64 {295627F8-6235-4E9D-992F-F200A7F40173}.ReleaseP|Win32.ActiveCfg = Release|Win32 {295627F8-6235-4E9D-992F-F200A7F40173}.ReleaseP|x64.ActiveCfg = Release|x64 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Debug|Win32.ActiveCfg = Debug|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Debug|Win32.Build.0 = Debug|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Debug|x64.ActiveCfg = Debug|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Debug|x64.Build.0 = Debug|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Release|Win32.ActiveCfg = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Release|Win32.Build.0 = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Release|x64.ActiveCfg = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Release|x64.Build.0 = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.ReleaseP|Win32.ActiveCfg = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.ReleaseP|Win32.Build.0 = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.ReleaseP|x64.ActiveCfg = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.ReleaseP|x64.Build.0 = Release|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Debug|Win32.ActiveCfg = Debug|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Debug|Win32.Build.0 = Debug|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Debug|x64.ActiveCfg = Debug|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Debug|x64.Build.0 = Debug|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Release|Win32.ActiveCfg = Release|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Release|Win32.Build.0 = Release|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Release|x64.ActiveCfg = Release|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Release|x64.Build.0 = Release|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.ReleaseP|Win32.ActiveCfg = Release|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.ReleaseP|x64.ActiveCfg = Release|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.ReleaseP|x64.Build.0 = Release|x64 EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE EndGlobalSection GlobalSection(NestedProjects) = preSolution {A6B8E42F-4793-4995-9D63-2906375407AD} = {8D08569A-D3CE-4690-A244-AA1704ED3147} {81EA1BB3-2BA0-4600-9081-2D2CB9203466} = {8D08569A-D3CE-4690-A244-AA1704ED3147} {949B73FF-BD75-47C0-B965-328513C481B4} = {8D08569A-D3CE-4690-A244-AA1704ED3147} {662C79E3-70D3-4F83-BAAF-EC663B93BAFD} = {2C836544-04C4-4839-AAF0-CE9526E167F6} {890C6C24-55F8-466B-91BE-221F6214C3B8} = {2C836544-04C4-4839-AAF0-CE9526E167F6} {E595EE31-3670-4F99-AAC0-C06B2B5D02E9} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {533889C9-1598-4823-BFA9-7C97FD35D6DF} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {1A7358F8-3F30-4079-8BAB-9399B76B5187} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {DA677405-57CD-4E24-AC27-4250A4BF0D1C} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {571D4215-38A0-42CE-8AB7-DEEE9D2154ED} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {4B152319-0AF6-4E1B-A284-805D6483C5F1} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {0AB48E5D-FAA5-402B-84D6-2F5166D90DD4} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {15CBFEFF-7965-41F5-B4E2-21E8795C9159} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {3A214E06-B95E-4D61-A291-1F8DF2EC10FD} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {BC845F0A-9F4D-4A2F-8366-30B816498DBD} = {4A43E150-27F3-4779-B894-9D5471CB90F9} {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF} = {4A43E150-27F3-4779-B894-9D5471CB90F9} {295627F8-6235-4E9D-992F-F200A7F40173} = {4A43E150-27F3-4779-B894-9D5471CB90F9} {44E47ABA-9695-4A96-BC52-53585C6AAA3C} = {176EBD88-B63B-466F-BB4F-3C331C89BF24} {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160} = {5B05DB5E-5941-4418-A8D1-37101F2A8E07} EndGlobalSection EndGlobal ================================================ FILE: src/infrarecorder_vc10.sln ================================================ Microsoft Visual Studio Solution File, Format Version 11.00 # Visual Studio 2010 Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "tools", "tools", "{2C836544-04C4-4839-AAF0-CE9526E167F6}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "main", "main", "{8D08569A-D3CE-4690-A244-AA1704ED3147}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "codecs", "codecs", "{B13D61CA-7A76-4A61-A488-2F8D06DAF06C}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "dependencies", "dependencies", "{342929BB-3FEE-47E9-A6ED-C391DE6A018D}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "setup", "setup", "{4A43E150-27F3-4779-B894-9D5471CB90F9}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "help", "help", "{176EBD88-B63B-466F-BB4F-3C331C89BF24}" EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "tests", "tests", "{5B05DB5E-5941-4418-A8D1-37101F2A8E07}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "infrarecorder", "app\infrarecorder_vc10.vcxproj", "{949B73FF-BD75-47C0-B965-328513C481B4}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shell", "shell\shell_vc10.vcxproj", "{A6B8E42F-4793-4995-9D63-2906375407AD}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "base", "base\base_vc10.vcxproj", "{81EA1BB3-2BA0-4600-9081-2D2CB9203466}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "codectester", "tools\codectester\codectester_vc10.vcxproj", "{662C79E3-70D3-4F83-BAAF-EC663B93BAFD}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "translationtool", "tools\translationtool\translationtool_vc10.vcxproj", "{890C6C24-55F8-466B-91BE-221F6214C3B8}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "lame", "codecs\lame\lame_vc10.vcxproj", "{E595EE31-3670-4F99-AAC0-C06B2B5D02E9}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libmp3lame-static", "..\dep\lame\vc_solution\vc9_libmp3lame.vcxproj", "{20536101-3B0E-43EF-94F9-080D595DAC57}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libmpghip-static", "..\dep\lame\vc_solution\vc9_mpglib.vcxproj", "{E2DAB91A-8248-4625-8A85-2C2C2A390DD8}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "sndfile", "codecs\sndfile\sndfile_vc10.vcxproj", "{533889C9-1598-4823-BFA9-7C97FD35D6DF}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "wave", "codecs\wave\wave_vc10.vcxproj", "{1A7358F8-3F30-4079-8BAB-9399B76B5187}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "wma", "codecs\wma\wma_vc10.vcxproj", "{DA677405-57CD-4E24-AC27-4250A4BF0D1C}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "vorbis", "codecs\vorbis\vorbis_vc10.vcxproj", "{571D4215-38A0-42CE-8AB7-DEEE9D2154ED}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libogg_static", "..\dep\libogg\win32\VS2010\libogg_static.vcxproj", "{15CBFEFF-7965-41F5-B4E2-21E8795C9159}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libvorbis_static", "..\dep\libvorbis\win32\VS2010\libvorbis\libvorbis_static.vcxproj", "{3A214E06-B95E-4D61-A291-1F8DF2EC10FD}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libvorbisfile", "..\dep\libvorbis\win32\VS2010\libvorbisfile\libvorbisfile_static.vcxproj", "{CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ir_plugin", "setup\ir_plugin\ir_plugin_vc10.vcxproj", "{BC845F0A-9F4D-4A2F-8366-30B816498DBD}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "setup_nsis", "setup\setup_nsis_vc10.vcxproj", "{B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "setup_wix", "setup\setup_wix_vc10.vcxproj", "{295627F8-6235-4E9D-992F-F200A7F40173}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "help_english", "..\doc\english\help_english_vc10.vcxproj", "{44E47ABA-9695-4A96-BC52-53585C6AAA3C}" EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tests", "tests\tests_vc10.vcxproj", "{2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}" EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Win32 = Debug|Win32 Debug|x64 = Debug|x64 Release|Win32 = Release|Win32 Release|x64 = Release|x64 ReleaseP|Win32 = ReleaseP|Win32 ReleaseP|x64 = ReleaseP|x64 EndGlobalSection GlobalSection(ProjectConfigurationPlatforms) = postSolution {949B73FF-BD75-47C0-B965-328513C481B4}.Debug|Win32.ActiveCfg = Debug|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.Debug|Win32.Build.0 = Debug|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.Debug|x64.ActiveCfg = Debug|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.Debug|x64.Build.0 = Debug|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.Release|Win32.ActiveCfg = Release|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.Release|Win32.Build.0 = Release|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.Release|x64.ActiveCfg = Release|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.Release|x64.Build.0 = Release|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.ReleaseP|Win32.ActiveCfg = ReleaseP|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.ReleaseP|Win32.Build.0 = ReleaseP|Win32 {949B73FF-BD75-47C0-B965-328513C481B4}.ReleaseP|x64.ActiveCfg = ReleaseP|x64 {949B73FF-BD75-47C0-B965-328513C481B4}.ReleaseP|x64.Build.0 = ReleaseP|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.Debug|Win32.ActiveCfg = Debug|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.Debug|Win32.Build.0 = Debug|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.Debug|x64.ActiveCfg = Debug|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.Debug|x64.Build.0 = Debug|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.Release|Win32.ActiveCfg = Release|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.Release|Win32.Build.0 = Release|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.Release|x64.ActiveCfg = Release|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.Release|x64.Build.0 = Release|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.ReleaseP|Win32.ActiveCfg = ReleaseP|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.ReleaseP|Win32.Build.0 = ReleaseP|Win32 {A6B8E42F-4793-4995-9D63-2906375407AD}.ReleaseP|x64.ActiveCfg = ReleaseP|x64 {A6B8E42F-4793-4995-9D63-2906375407AD}.ReleaseP|x64.Build.0 = ReleaseP|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Debug|Win32.ActiveCfg = Debug|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Debug|Win32.Build.0 = Debug|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Debug|x64.ActiveCfg = Debug|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Debug|x64.Build.0 = Debug|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Release|Win32.ActiveCfg = Release|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Release|Win32.Build.0 = Release|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Release|x64.ActiveCfg = Release|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.Release|x64.Build.0 = Release|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.ReleaseP|Win32.ActiveCfg = Release|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.ReleaseP|Win32.Build.0 = Release|Win32 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.ReleaseP|x64.ActiveCfg = Release|x64 {81EA1BB3-2BA0-4600-9081-2D2CB9203466}.ReleaseP|x64.Build.0 = Release|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Debug|Win32.ActiveCfg = Debug|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Debug|Win32.Build.0 = Debug|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Debug|x64.ActiveCfg = Debug|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Debug|x64.Build.0 = Debug|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Release|Win32.ActiveCfg = Release|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Release|Win32.Build.0 = Release|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Release|x64.ActiveCfg = Release|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.Release|x64.Build.0 = Release|x64 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.ReleaseP|Win32.ActiveCfg = Release|Win32 {662C79E3-70D3-4F83-BAAF-EC663B93BAFD}.ReleaseP|x64.ActiveCfg = Release|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Debug|Win32.ActiveCfg = Debug|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Debug|Win32.Build.0 = Debug|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Debug|x64.ActiveCfg = Debug|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Debug|x64.Build.0 = Debug|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Release|Win32.ActiveCfg = Release|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Release|Win32.Build.0 = Release|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Release|x64.ActiveCfg = Release|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.Release|x64.Build.0 = Release|x64 {890C6C24-55F8-466B-91BE-221F6214C3B8}.ReleaseP|Win32.ActiveCfg = Release|Win32 {890C6C24-55F8-466B-91BE-221F6214C3B8}.ReleaseP|x64.ActiveCfg = Release|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Debug|Win32.ActiveCfg = Debug|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Debug|Win32.Build.0 = Debug|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Debug|x64.ActiveCfg = Debug|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Debug|x64.Build.0 = Debug|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Release|Win32.ActiveCfg = Release|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Release|Win32.Build.0 = Release|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Release|x64.ActiveCfg = Release|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.Release|x64.Build.0 = Release|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.ReleaseP|Win32.ActiveCfg = Release|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.ReleaseP|Win32.Build.0 = Release|Win32 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.ReleaseP|x64.ActiveCfg = Release|x64 {E595EE31-3670-4F99-AAC0-C06B2B5D02E9}.ReleaseP|x64.Build.0 = Release|x64 {20536101-3B0E-43EF-94F9-080D595DAC57}.Debug|Win32.ActiveCfg = Debug|Win32 {20536101-3B0E-43EF-94F9-080D595DAC57}.Debug|Win32.Build.0 = Debug|Win32 {20536101-3B0E-43EF-94F9-080D595DAC57}.Debug|x64.ActiveCfg = Debug|x64 {20536101-3B0E-43EF-94F9-080D595DAC57}.Debug|x64.Build.0 = Debug|x64 {20536101-3B0E-43EF-94F9-080D595DAC57}.Release|Win32.ActiveCfg = Release|Win32 {20536101-3B0E-43EF-94F9-080D595DAC57}.Release|Win32.Build.0 = Release|Win32 {20536101-3B0E-43EF-94F9-080D595DAC57}.Release|x64.ActiveCfg = Release|x64 {20536101-3B0E-43EF-94F9-080D595DAC57}.Release|x64.Build.0 = Release|x64 {20536101-3B0E-43EF-94F9-080D595DAC57}.ReleaseP|Win32.ActiveCfg = Release|Win32 {20536101-3B0E-43EF-94F9-080D595DAC57}.ReleaseP|Win32.Build.0 = Release|Win32 {20536101-3B0E-43EF-94F9-080D595DAC57}.ReleaseP|x64.ActiveCfg = Release|x64 {20536101-3B0E-43EF-94F9-080D595DAC57}.ReleaseP|x64.Build.0 = Release|x64 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.Debug|Win32.ActiveCfg = Debug|Win32 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.Debug|Win32.Build.0 = Debug|Win32 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.Debug|x64.ActiveCfg = Debug|x64 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.Debug|x64.Build.0 = Debug|x64 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.Release|Win32.ActiveCfg = Release|Win32 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.Release|Win32.Build.0 = Release|Win32 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.Release|x64.ActiveCfg = Release|x64 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.Release|x64.Build.0 = Release|x64 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.ReleaseP|Win32.ActiveCfg = Release|Win32 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.ReleaseP|Win32.Build.0 = Release|Win32 {E2DAB91A-8248-4625-8A85-2C2C2A390DD8}.ReleaseP|x64.ActiveCfg = Release|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Debug|Win32.ActiveCfg = Debug|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Debug|Win32.Build.0 = Debug|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Debug|x64.ActiveCfg = Debug|x64 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Debug|x64.Build.0 = Debug|x64 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Release|Win32.ActiveCfg = Release|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Release|Win32.Build.0 = Release|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Release|x64.ActiveCfg = Release|x64 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.Release|x64.Build.0 = Release|x64 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.ReleaseP|Win32.ActiveCfg = Release|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.ReleaseP|Win32.Build.0 = Release|Win32 {533889C9-1598-4823-BFA9-7C97FD35D6DF}.ReleaseP|x64.ActiveCfg = Release|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Debug|Win32.ActiveCfg = Debug|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Debug|Win32.Build.0 = Debug|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Debug|x64.ActiveCfg = Debug|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Debug|x64.Build.0 = Debug|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Release|Win32.ActiveCfg = Release|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Release|Win32.Build.0 = Release|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Release|x64.ActiveCfg = Release|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.Release|x64.Build.0 = Release|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.ReleaseP|Win32.ActiveCfg = Release|Win32 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.ReleaseP|x64.ActiveCfg = Release|x64 {1A7358F8-3F30-4079-8BAB-9399B76B5187}.ReleaseP|x64.Build.0 = Release|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Debug|Win32.ActiveCfg = Debug|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Debug|Win32.Build.0 = Debug|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Debug|x64.ActiveCfg = Debug|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Debug|x64.Build.0 = Debug|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Release|Win32.ActiveCfg = Release|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Release|Win32.Build.0 = Release|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Release|x64.ActiveCfg = Release|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.Release|x64.Build.0 = Release|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.ReleaseP|Win32.ActiveCfg = Release|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.ReleaseP|Win32.Build.0 = Release|Win32 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.ReleaseP|x64.ActiveCfg = Release|x64 {DA677405-57CD-4E24-AC27-4250A4BF0D1C}.ReleaseP|x64.Build.0 = Release|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Debug|Win32.ActiveCfg = Debug|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Debug|Win32.Build.0 = Debug|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Debug|x64.ActiveCfg = Debug|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Debug|x64.Build.0 = Debug|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Release|Win32.ActiveCfg = Release|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Release|Win32.Build.0 = Release|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Release|x64.ActiveCfg = Release|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.Release|x64.Build.0 = Release|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.ReleaseP|Win32.ActiveCfg = Release|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.ReleaseP|Win32.Build.0 = Release|Win32 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.ReleaseP|x64.ActiveCfg = Release|x64 {571D4215-38A0-42CE-8AB7-DEEE9D2154ED}.ReleaseP|x64.Build.0 = Release|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Debug|Win32.ActiveCfg = Debug|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Debug|Win32.Build.0 = Debug|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Debug|x64.ActiveCfg = Debug|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Debug|x64.Build.0 = Debug|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Release|Win32.ActiveCfg = Release|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Release|Win32.Build.0 = Release|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Release|x64.ActiveCfg = Release|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.Release|x64.Build.0 = Release|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.ReleaseP|Win32.ActiveCfg = Release|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.ReleaseP|Win32.Build.0 = Release|Win32 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.ReleaseP|x64.ActiveCfg = Release|x64 {15CBFEFF-7965-41F5-B4E2-21E8795C9159}.ReleaseP|x64.Build.0 = Release|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Debug|Win32.ActiveCfg = Debug|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Debug|Win32.Build.0 = Debug|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Debug|x64.ActiveCfg = Debug|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Debug|x64.Build.0 = Debug|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Release|Win32.ActiveCfg = Release|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Release|Win32.Build.0 = Release|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Release|x64.ActiveCfg = Release|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.Release|x64.Build.0 = Release|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.ReleaseP|Win32.ActiveCfg = Release|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.ReleaseP|Win32.Build.0 = Release|Win32 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.ReleaseP|x64.ActiveCfg = Release|x64 {3A214E06-B95E-4D61-A291-1F8DF2EC10FD}.ReleaseP|x64.Build.0 = Release|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Debug|Win32.ActiveCfg = Debug|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Debug|Win32.Build.0 = Debug|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Debug|x64.ActiveCfg = Debug|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Debug|x64.Build.0 = Debug|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Release|Win32.ActiveCfg = Release|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Release|Win32.Build.0 = Release|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Release|x64.ActiveCfg = Release|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.Release|x64.Build.0 = Release|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.ReleaseP|Win32.ActiveCfg = Release|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.ReleaseP|Win32.Build.0 = Release|Win32 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.ReleaseP|x64.ActiveCfg = Release|x64 {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC}.ReleaseP|x64.Build.0 = Release|x64 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Debug|Win32.ActiveCfg = Debug|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Debug|Win32.Build.0 = Debug|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Debug|x64.ActiveCfg = Debug|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Release|Win32.ActiveCfg = Release|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Release|Win32.Build.0 = Release|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.Release|x64.ActiveCfg = Release|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.ReleaseP|Win32.ActiveCfg = Release|Win32 {BC845F0A-9F4D-4A2F-8366-30B816498DBD}.ReleaseP|x64.ActiveCfg = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Debug|Win32.ActiveCfg = Debug|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Debug|x64.ActiveCfg = Debug|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Release|Win32.ActiveCfg = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Release|Win32.Build.0 = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.Release|x64.ActiveCfg = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.ReleaseP|Win32.ActiveCfg = Release|Win32 {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF}.ReleaseP|x64.ActiveCfg = Release|Win32 {295627F8-6235-4E9D-992F-F200A7F40173}.Debug|Win32.ActiveCfg = Debug|Win32 {295627F8-6235-4E9D-992F-F200A7F40173}.Debug|x64.ActiveCfg = Debug|x64 {295627F8-6235-4E9D-992F-F200A7F40173}.Release|Win32.ActiveCfg = Release|Win32 {295627F8-6235-4E9D-992F-F200A7F40173}.Release|x64.ActiveCfg = Release|x64 {295627F8-6235-4E9D-992F-F200A7F40173}.Release|x64.Build.0 = Release|x64 {295627F8-6235-4E9D-992F-F200A7F40173}.ReleaseP|Win32.ActiveCfg = Release|Win32 {295627F8-6235-4E9D-992F-F200A7F40173}.ReleaseP|x64.ActiveCfg = Release|x64 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Debug|Win32.ActiveCfg = Debug|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Debug|Win32.Build.0 = Debug|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Debug|x64.ActiveCfg = Debug|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Debug|x64.Build.0 = Debug|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Release|Win32.ActiveCfg = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Release|Win32.Build.0 = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Release|x64.ActiveCfg = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.Release|x64.Build.0 = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.ReleaseP|Win32.ActiveCfg = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.ReleaseP|Win32.Build.0 = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.ReleaseP|x64.ActiveCfg = Release|Win32 {44E47ABA-9695-4A96-BC52-53585C6AAA3C}.ReleaseP|x64.Build.0 = Release|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Debug|Win32.ActiveCfg = Debug|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Debug|Win32.Build.0 = Debug|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Debug|x64.ActiveCfg = Debug|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Debug|x64.Build.0 = Debug|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Release|Win32.ActiveCfg = Release|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Release|Win32.Build.0 = Release|Win32 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Release|x64.ActiveCfg = Release|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.Release|x64.Build.0 = Release|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.ReleaseP|Win32.ActiveCfg = Release|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.ReleaseP|x64.ActiveCfg = Release|x64 {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160}.ReleaseP|x64.Build.0 = Release|x64 EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE EndGlobalSection GlobalSection(NestedProjects) = preSolution {662C79E3-70D3-4F83-BAAF-EC663B93BAFD} = {2C836544-04C4-4839-AAF0-CE9526E167F6} {890C6C24-55F8-466B-91BE-221F6214C3B8} = {2C836544-04C4-4839-AAF0-CE9526E167F6} {949B73FF-BD75-47C0-B965-328513C481B4} = {8D08569A-D3CE-4690-A244-AA1704ED3147} {A6B8E42F-4793-4995-9D63-2906375407AD} = {8D08569A-D3CE-4690-A244-AA1704ED3147} {81EA1BB3-2BA0-4600-9081-2D2CB9203466} = {8D08569A-D3CE-4690-A244-AA1704ED3147} {E595EE31-3670-4F99-AAC0-C06B2B5D02E9} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {533889C9-1598-4823-BFA9-7C97FD35D6DF} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {1A7358F8-3F30-4079-8BAB-9399B76B5187} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {DA677405-57CD-4E24-AC27-4250A4BF0D1C} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {571D4215-38A0-42CE-8AB7-DEEE9D2154ED} = {B13D61CA-7A76-4A61-A488-2F8D06DAF06C} {20536101-3B0E-43EF-94F9-080D595DAC57} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {E2DAB91A-8248-4625-8A85-2C2C2A390DD8} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {15CBFEFF-7965-41F5-B4E2-21E8795C9159} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {3A214E06-B95E-4D61-A291-1F8DF2EC10FD} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {CEBDE98B-A6AA-46E6-BC79-FAAF823DB9EC} = {342929BB-3FEE-47E9-A6ED-C391DE6A018D} {BC845F0A-9F4D-4A2F-8366-30B816498DBD} = {4A43E150-27F3-4779-B894-9D5471CB90F9} {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF} = {4A43E150-27F3-4779-B894-9D5471CB90F9} {295627F8-6235-4E9D-992F-F200A7F40173} = {4A43E150-27F3-4779-B894-9D5471CB90F9} {44E47ABA-9695-4A96-BC52-53585C6AAA3C} = {176EBD88-B63B-466F-BB4F-3C331C89BF24} {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160} = {5B05DB5E-5941-4418-A8D1-37101F2A8E07} EndGlobalSection EndGlobal ================================================ FILE: src/setup/ir_plugin/ir_plugin.cc ================================================ /* * Copyright (C) 2006-2012 Christian Kindahl, christian dot kindahl at gmail dot com * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ #include "stdafx.hh" #include #include #include "settings.hh" typedef struct _stack_t { struct _stack_t *pNext; char szText[1]; // This should be the length of iStringSize. } stack_t; BOOL APIENTRY DllMain(HANDLE hModule, DWORD ul_reason_for_call, LPVOID lpReserved) { return TRUE; } bool GetConfigPath(TCHAR *szConfigPath) { if (!SUCCEEDED(SHGetFolderPath(HWND_DESKTOP,CSIDL_APPDATA | CSIDL_FLAG_CREATE,NULL, SHGFP_TYPE_CURRENT,szConfigPath))) return false; IncludeTrailingBackslash(szConfigPath); lstrcat(szConfigPath,_T("InfraRecorder\\")); // Create the file path if it doesn't exist. ckcore::Directory::create(szConfigPath); lstrcat(szConfigPath,_T("settings.xml")); return true; } void __declspec(dllexport) CreateConfig(HWND hWndParent,int iStringSize, char *szVariables,stack_t **ppStackTop) { // The config file name is on the top of the stack. TCHAR szConfigFileName[MAX_PATH]; stack_t *pStackEntry = *ppStackTop; // UPDATE: The first is now ignored since the configuration file is // stored in a common place. GetConfigPath(szConfigFileName); pStackEntry = pStackEntry->pNext; AnsiToUnicode(g_LanguageSettings.m_szLanguageFile,pStackEntry->szText,MAX_PATH); // Only create new config file if one does not already exist. if (!ckcore::File::exist(szConfigFileName)) { // Save the config file. CXmlProcessor Xml; Xml.AddElement(_T("InfraRecorder"),_T(""),true); Xml.AddElement(_T("Settings"),_T(""),true); g_LanguageSettings.Save(&Xml); Xml.LeaveElement(); Xml.LeaveElement(); Xml.Save(szConfigFileName); } } ================================================ FILE: src/setup/ir_plugin/ir_plugin.def ================================================ LIBRARY ir_plugin EXPORTS CreateConfig ================================================ FILE: src/setup/ir_plugin/ir_plugin_vc08.vcproj ================================================ ================================================ FILE: src/setup/ir_plugin/ir_plugin_vc10.vcxproj ================================================  Debug Win32 Release Win32 ir_plugin {BC845F0A-9F4D-4A2F-8366-30B816498DBD} ir_plugin Win32Proj DynamicLibrary Unicode DynamicLibrary Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) Disabled $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_WINDOWS;_USRDLL;IRINSTALLPLUGIN_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 EditAndContinue ckcored.lib;%(AdditionalDependencies) ir_plugin.def true $(OutDir)ir_plugin.pdb Windows $(OutDir)ir_plugin.lib MachineX86 $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_WINDOWS;_USRDLL;IRINSTALLPLUGIN_EXPORTS;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) ir_plugin.def true Windows true true $(OutDir)ir_plugin.lib MachineX86 stdafx.hh stdafx.hh stdafx.hh stdafx.hh Create stdafx.hh Create stdafx.hh {81ea1bb3-2ba0-4600-9081-2d2cb9203466} false ================================================ FILE: src/setup/ir_plugin/ir_plugin_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx Source Files Source Files Source Files Source Files Header Files Header Files ================================================ FILE: src/setup/ir_plugin/settings.cc ================================================ /* * Copyright (C) 2006-2012 Christian Kindahl, christian dot kindahl at gmail dot com * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ #include "stdafx.hh" #include "settings.hh" CLanguageSettings g_LanguageSettings; bool CLanguageSettings::Save(CXmlProcessor *pXML) { if (pXML == NULL) return false; pXML->AddElement(_T("Language"),_T(""),true); pXML->AddElement(_T("LanguageFile"),m_szLanguageFile); pXML->LeaveElement(); return true; } bool CLanguageSettings::Load(CXmlProcessor *pXML) { if (pXML == NULL) return false; if (!pXML->EnterElement(_T("Language"))) return false; pXML->GetSafeElementData(_T("LanguageFile"),m_szLanguageFile,MAX_PATH - 1); if (ckcore::File::exist(m_szLanguageFile)) { m_pLngProcessor = new CLngProcessor(m_szLanguageFile); m_pLngProcessor->Load(); } pXML->LeaveElement(); return true; } ================================================ FILE: src/setup/ir_plugin/settings.hh ================================================ /* * Copyright (C) 2006-2012 Christian Kindahl, christian dot kindahl at gmail dot com * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ #pragma once #include #include #include #include class ISettings { public: virtual bool Save(CXmlProcessor *pXML) = 0; virtual bool Load(CXmlProcessor *pXML) = 0; }; class CLanguageSettings : public ISettings { public: TCHAR m_szLanguageFile[MAX_PATH]; CLngProcessor *m_pLngProcessor; CLanguageSettings() { m_szLanguageFile[0] = '\0'; m_pLngProcessor = NULL; } ~CLanguageSettings() { if (m_pLngProcessor != NULL) { delete m_pLngProcessor; m_pLngProcessor = NULL; } } bool Save(CXmlProcessor *pXML); bool Load(CXmlProcessor *pXML); }; extern CLanguageSettings g_LanguageSettings; ================================================ FILE: src/setup/ir_plugin/stdafx.cc ================================================ /* * Copyright (C) 2006-2012 Christian Kindahl, christian dot kindahl at gmail dot com * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ #include "stdafx.hh" ================================================ FILE: src/setup/ir_plugin/stdafx.hh ================================================ /* * Copyright (C) 2006-2012 Christian Kindahl, christian dot kindahl at gmail dot com * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */ #pragma once #define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers #include #include #include #ifndef _T #define _T TEXT #endif ================================================ FILE: src/setup/setup_nsis.nsi ================================================ ; Infra Recorder Installation Script ; written by Christian Kindahl ; ;-------------------------------- ; Include Modern UI !include "MUI.nsh" !include "LogicLib.nsh" !include "FileFunc.nsh" ;-------------------------------- ; Definitions !define MUI_COMPONENTSPAGE_SMALLDESC ;!define MUI_HEADERIMAGE ;!define MUI_HEADERIMAGE_BITMAP "resources\header-logo.bmp" ;!define MUI_HEADERIMAGE_RIGHT !define MUI_ABORTWARNING ;-------------------------------- ; Plugins !addplugindir ir_plugin\win32\release\ ;-------------------------------- ; StrStr function. Function StrStr ; Get input from user Exch $R0 Exch Exch $R1 Push $R2 Push $R3 Push $R4 Push $R5 ; Get "String" and "SubString" length StrLen $R2 $R0 StrLen $R3 $R1 ; Start "StartCharPos" counter StrCpy $R4 0 ; Loop until "SubString" is found or "String" reaches its end ${Do} ; Remove everything before and after the searched part ("TempStr") StrCpy $R5 $R1 $R2 $R4 ; Compare "TempStr" with "SubString" ${IfThen} $R5 == $R0 ${|} ${ExitDo} ${|} ; If not "SubString", this could be "String"'s end ${IfThen} $R4 >= $R3 ${|} ${ExitDo} ${|} ; If not, continue the loop IntOp $R4 $R4 + 1 ${Loop} ; Remove part before "SubString" on "String" (if there has one) StrCpy $R0 $R1 `` $R4 ; Return output to user Pop $R5 Pop $R4 Pop $R3 Pop $R2 Pop $R1 Exch $R0 FunctionEnd ;-------------------------------- ; StrLower function Function StrLower Exch $0 ; Original string Push $1 ; Final string Push $2 ; Current character Push $3 Push $4 StrCpy $1 "" Loop: StrCpy $2 $0 1 ; Get next character StrCmp $2 "" Done StrCpy $0 $0 "" 1 StrCpy $3 122 ; 122 = ASCII code for z Loop2: IntFmt $4 %c $3 ; Get character from current ASCII code StrCmp $2 $4 Match IntOp $3 $3 - 1 StrCmp $3 91 NoMatch Loop2 ; 90 = ASCII code one beyond Z Match: StrCpy $2 $4 ; It 'matches' (either case) so grab the lowercase version NoMatch: StrCpy $1 $1$2 ; Append to the final string Goto Loop Done: StrCpy $0 $1 ; Return the final string Pop $4 Pop $3 Pop $2 Pop $1 Exch $0 FunctionEnd ;-------------------------------- ; General ; Application name. Name "InfraRecorder" ; Default installation folder. InstallDir "$PROGRAMFILES\InfraRecorder" ; Get installation folder from registry if available. InstallDirRegKey HKCU "Software\InfraRecorder" "" !ifdef INNER !echo "Inner invocation" ; Output file. OutFile "$%TEMP%\ir.exe" ; Compression settings. SetCompress off !else !echo "Outer invocation" ; Call makensis again, defining INNER. This writes an installer for us which, ; when it is invoked, will just write the uninstaller to some location, and ; then exit. !system "$\"${NSISDIR}\makensis$\" /DINNER setup_nsis.nsi" = 0 ; Run that installer we just created. Since it calls quit the return value ; isn't zero. !system "$%TEMP%\ir.exe" = 2 ; That will have written an uninstaller binary for us. Now we sign it. !system "call ..\..\sign.bat $%TEMP%\uninstall.exe" = 0 ; Output file. OutFile "..\..\dist\ir.exe" ; Compression settings. ;SetCompress off SetCompress force SetCompressor /SOLID lzma !endif ;-------------------------------- ; Pages !insertmacro MUI_PAGE_WELCOME !insertmacro MUI_PAGE_LICENSE "..\..\license.txt" !insertmacro MUI_PAGE_COMPONENTS !insertmacro MUI_PAGE_DIRECTORY !insertmacro MUI_PAGE_INSTFILES !insertmacro MUI_UNPAGE_WELCOME !insertmacro MUI_UNPAGE_CONFIRM !insertmacro MUI_UNPAGE_INSTFILES ;-------------------------------- ; Languages !insertmacro MUI_LANGUAGE "Arabic" ; !insertmacro MUI_LANGUAGE "Armenian" !insertmacro MUI_LANGUAGE "Basque" !insertmacro MUI_LANGUAGE "Bosnian" !insertmacro MUI_LANGUAGE "Bulgarian" !insertmacro MUI_LANGUAGE "Catalan" !insertmacro MUI_LANGUAGE "SimpChinese" !insertmacro MUI_LANGUAGE "TradChinese" ; !insertmacro MUI_LANGUAGE "Chuvash" !insertmacro MUI_LANGUAGE "Croatian" !insertmacro MUI_LANGUAGE "Czech" !insertmacro MUI_LANGUAGE "Danish" !insertmacro MUI_LANGUAGE "Dutch" !insertmacro MUI_LANGUAGE "English" !insertmacro MUI_LANGUAGE "Estonian" !insertmacro MUI_LANGUAGE "Farsi" !insertmacro MUI_LANGUAGE "Finnish" !insertmacro MUI_LANGUAGE "French" !insertmacro MUI_LANGUAGE "Galician" !insertmacro MUI_LANGUAGE "German" ; !insertmacro MUI_LANGUAGE "Georgian" !insertmacro MUI_LANGUAGE "Greek" !insertmacro MUI_LANGUAGE "Hebrew" !insertmacro MUI_LANGUAGE "Hungarian" !insertmacro MUI_LANGUAGE "Indonesian" !insertmacro MUI_LANGUAGE "Italian" !insertmacro MUI_LANGUAGE "Japanese" !insertmacro MUI_LANGUAGE "Korean" !insertmacro MUI_LANGUAGE "Latvian" !insertmacro MUI_LANGUAGE "Lithuanian" !insertmacro MUI_LANGUAGE "Macedonian" !insertmacro MUI_LANGUAGE "Norwegian" !insertmacro MUI_LANGUAGE "Polish" !insertmacro MUI_LANGUAGE "Portuguese" !insertmacro MUI_LANGUAGE "PortugueseBR" !insertmacro MUI_LANGUAGE "Romanian" !insertmacro MUI_LANGUAGE "Russian" !insertmacro MUI_LANGUAGE "Serbian" !insertmacro MUI_LANGUAGE "SerbianLatin" !insertmacro MUI_LANGUAGE "Slovak" !insertmacro MUI_LANGUAGE "Slovenian" !insertmacro MUI_LANGUAGE "Spanish" !insertmacro MUI_LANGUAGE "Swedish" !insertmacro MUI_LANGUAGE "Thai" !insertmacro MUI_LANGUAGE "Turkish" !insertmacro MUI_LANGUAGE "Ukrainian" ; !insertmacro MUI_LANGUAGE "Valencian" ; !insertmacro MUI_LANGUAGE "Vietnamese" ;-------------------------------- ; A customized language selection dialog. !macro IR_MUI_LANGDLL_DISPLAY !verbose push !verbose ${MUI_VERBOSE} !ifdef NSIS_CONFIG_SILENT_SUPPORT IfSilent mui.langdll_done !endif !insertmacro MUI_DEFAULT MUI_LANGDLL_WINDOWTITLE "InfraRecorder Language" !insertmacro MUI_DEFAULT MUI_LANGDLL_INFO "Please select a language to use in InfraRecorder." !ifdef MUI_LANGDLL_REGISTRY_ROOT & MUI_LANGDLL_REGISTRY_KEY & MUI_LANGDLL_REGISTRY_VALUENAME ReadRegStr $MUI_TEMP1 "${MUI_LANGDLL_REGISTRY_ROOT}" "${MUI_LANGDLL_REGISTRY_KEY}" "${MUI_LANGDLL_REGISTRY_VALUENAME}" StrCmp $MUI_TEMP1 "" mui.langdll_show StrCpy $LANGUAGE $MUI_TEMP1 !ifndef MUI_LANGDLL_ALWAYSSHOW Goto mui.langdll_done !endif mui.langdll_show: !endif LangDLL::LangDialog "${MUI_LANGDLL_WINDOWTITLE}" "${MUI_LANGDLL_INFO}" A ${MUI_LANGDLL_LANGUAGES} "" ; !ifdef MUI_LANGDLL_ALLLANGUAGES ; LangDLL::LangDialog "${MUI_LANGDLL_WINDOWTITLE}" "${MUI_LANGDLL_INFO}" A ${MUI_LANGDLL_LANGUAGES} "" ; !else ; LangDLL::LangDialog "${MUI_LANGDLL_WINDOWTITLE}" "${MUI_LANGDLL_INFO}" AC ${MUI_LANGDLL_LANGUAGES_CP} "" ; !endif Pop $LANGUAGE StrCmp $LANGUAGE "cancel" 0 +2 Abort !ifdef NSIS_CONFIG_SILENT_SUPPORT mui.langdll_done: !else ifdef MUI_LANGDLL_REGISTRY_ROOT & MUI_LANGDLL_REGISTRY_KEY & MUI_LANGDLL_REGISTRY_VALUENAME mui.langdll_done: !endif !verbose pop !macroend ;-------------------------------- ; Installation types InstType "Full" InstType "Minimal" ;-------------------------------- ; Installer Functions !insertmacro GetParameters Function .onInit !ifdef INNER ; If INNER is defined, then we aren't supposed to do anything except write ; out the installer. This is better than processing a command line option as ; it means this entire code path is not present in the final (real) ; installer. WriteUninstaller "$%TEMP%\uninstall.exe" Quit !endif ; Display the language selector. !insertmacro IR_MUI_LANGDLL_DISPLAY ; Parse the command-line. ;Call GetParameters ;Pop $3 ${GetParameters} $3 ;Search for quoted /LANGUAGE. StrCpy $2 '"' Push $3 Push '"/LANGUAGE=' Call StrStr Pop $1 StrCpy $1 $1 "" 1 # skip quote StrCmp $1 "" "" Next ;Search for non quoted /LANGUAGE. StrCpy $2 ' ' Push $3 Push '/LANGUAGE=' Call StrStr Pop $1 Next: StrCmp $1 "" done ;Copy the value after /LANGUAGE=. StrCpy $1 $1 "" 10 ; Search for the next parameter. Push $1 Push $2 Call StrStr Pop $2 StrCmp $2 "" Done StrLen $2 $2 StrCpy $1 $1 -$2 Done: ; Convert the language parameter to lowercase. Push $1 Call StrLower Pop $1 ;MessageBox MB_OK $1 ClearErrors UserInfo::GetName IfErrors Win9x UserInfo::GetAccountType Pop $0 StrCmp $0 "Admin" 0 +3 SetShellVarContext all Goto cont_done SetShellVarContext current Win9x: SetShellVarContext current cont_done: FunctionEnd ;-------------------------------- ; Language Strings ; Language strings (Albanian) LangString NAME_SecCore ${LANG_ALBANIAN} "Skedart baz t InfraRecorder (t domosdoshme)" LangString NAME_SecStartShortcut ${LANG_ALBANIAN} "Shkurtoret e Menus Start" LangString NAME_SecDeskShortcut ${LANG_ALBANIAN} "Shkurtore e Desktopit" LangString NAME_SecQuickShortcut ${LANG_ALBANIAN} "Shkurtore e hapjes s shpejt" LangString NAME_SecLang ${LANG_ALBANIAN} "Skedart e gjuhs" LangString DESC_SecCore ${LANG_ALBANIAN} "Skedart baz q duhen pr t prdorur InfraRecorder." LangString DESC_SecStartShortcut ${LANG_ALBANIAN} "Shto ikonat n menun start pr akses t shpejt." LangString DESC_SecDeskShortcut ${LANG_ALBANIAN} "Shto nj ikon n desktop." LangString DESC_SecQuickShortcut ${LANG_ALBANIAN} "Shto nj ikon n shiritin e hapjes s shpejt." LangString DESC_SecLang ${LANG_ALBANIAN} "Skedart e gjuhs q prdoren pr t mbshtetur gjuh t tjera n InfraRecorder." ; Language strings (Arabic) LangString NAME_SecCore ${LANG_ARABIC} " Infrarecorder ()" LangString NAME_SecStartShortcut ${LANG_ARABIC} " " LangString NAME_SecDeskShortcut ${LANG_ARABIC} " " LangString NAME_SecQuickShortcut ${LANG_ARABIC} " " LangString NAME_SecLang ${LANG_ARABIC} " " LangString DESC_SecCore ${LANG_ARABIC} " " LangString DESC_SecStartShortcut ${LANG_ARABIC} " " LangString DESC_SecDeskShortcut ${LANG_ARABIC} " " LangString DESC_SecQuickShortcut ${LANG_ARABIC} " " LangString DESC_SecLang ${LANG_ARABIC} " " ; Language strings (Armenian) LangString NAME_SecCore ${LANG_ARMENIAN} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_ARMENIAN} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_ARMENIAN} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_ARMENIAN} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_ARMENIAN} "Language Files" LangString DESC_SecCore ${LANG_ARMENIAN} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_ARMENIAN} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_ARMENIAN} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_ARMENIAN} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_ARMENIAN} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Basque) LangString NAME_SecCore ${LANG_BASQUE} "InfraRecorder Core Artxiboak (beharrezkoak)" LangString NAME_SecStartShortcut ${LANG_BASQUE} "Hasiera Menuaren Laburbideak" LangString NAME_SecDeskShortcut ${LANG_BASQUE} "Idazmahaiaren Laburbidea" LangString NAME_SecQuickShortcut ${LANG_BASQUE} "Laburbide Arina" LangString NAME_SecLang ${LANG_BASQUE} "Hizkuntza artxiboak" LangString DESC_SecCore ${LANG_BASQUE} "InfraRecorder erabiltzeko behar diren artxiboak" LangString DESC_SecStartShortcut ${LANG_BASQUE} "Ikonoak gehitzen dizkio zure hasiera menuari akzesoa errazagoa izan dadin" LangString DESC_SecDeskShortcut ${LANG_BASQUE} "Ikonoak gehitzen dizkio zure idazmahaiari" LangString DESC_SecQuickShortcut ${LANG_BASQUE} "Ikono bat gehitzen dio arin-hasteko barrari" LangString DESC_SecLang ${LANG_BASQUE} "Hizkuntza desberdinak onartzeko erabiltzen diren artxiboak" ; Language strings (Bosnian) LangString NAME_SecCore ${LANG_BOSNIAN} "Kljucna datoteka InfraRecorder-a (zahtijevano)" LangString NAME_SecStartShortcut ${LANG_BOSNIAN} "Precica za Start Menu" LangString NAME_SecDeskShortcut ${LANG_BOSNIAN} "Precica za Desktop" LangString NAME_SecQuickShortcut ${LANG_BOSNIAN} "Precica za Brzo pokretanje" LangString NAME_SecLang ${LANG_BOSNIAN} "Datoteke jezika" LangString DESC_SecCore ${LANG_BOSNIAN} "InfraRecorder zahtijeva kljucne datoteke." LangString DESC_SecStartShortcut ${LANG_BOSNIAN} "Dodaj ikonu u start menu za jednostavniji pristup." LangString DESC_SecDeskShortcut ${LANG_BOSNIAN} "Dodaj ikonu na desktop." LangString DESC_SecQuickShortcut ${LANG_BOSNIAN} "Dodaj ikonu za brzo pokretanje." LangString DESC_SecLang ${LANG_BOSNIAN} "Datoteke jezika se koriste za prikaz InfraRecorder-a u razlicitim jezicima." ; Language strings (Bulgarian) LangString NAME_SecCore ${LANG_BULGARIAN} " InfraRecorder ()" LangString NAME_SecStartShortcut ${LANG_BULGARIAN} " " LangString NAME_SecDeskShortcut ${LANG_BULGARIAN} " " LangString NAME_SecQuickShortcut ${LANG_BULGARIAN} " quick launch" LangString NAME_SecLang ${LANG_BULGARIAN} " " LangString DESC_SecCore ${LANG_BULGARIAN} " InfraRecorder" LangString DESC_SecStartShortcut ${LANG_BULGARIAN} " ." LangString DESC_SecDeskShortcut ${LANG_BULGARIAN} " " LangString DESC_SecQuickShortcut ${LANG_BULGARIAN} " quick launch" LangString DESC_SecLang ${LANG_BULGARIAN} " InfraRecorder" ; Language strings (Catalan) LangString NAME_SecCore ${LANG_CATALAN} "Fitxers del nucli InfraRecorder (necessari)" LangString NAME_SecStartShortcut ${LANG_CATALAN} "Dreceres en men Inici" LangString NAME_SecDeskShortcut ${LANG_CATALAN} "Drecera en Escriptori" LangString NAME_SecQuickShortcut ${LANG_CATALAN} "Drecera d'execuci rpida" LangString NAME_SecLang ${LANG_CATALAN} "Fitxers de idioma" LangString DESC_SecCore ${LANG_CATALAN} "Els fitxers del nucli necessaris per utilitzar el InfraRecorder." LangString DESC_SecStartShortcut ${LANG_CATALAN} "Afegeix icones al vostre men Inici per facilitar l'accs." LangString DESC_SecDeskShortcut ${LANG_CATALAN} "Afegeix una icona al vostre escriptori." LangString DESC_SecQuickShortcut ${LANG_CATALAN} "Afegeix una icona a la vostre barra d'execuci rpida." LangString DESC_SecLang ${LANG_CATALAN} "Fitxers de idioma utilitzats per donar suport a diferents idiomes en el InfraRecorder." ; Language strings (Croatian) LangString NAME_SecCore ${LANG_CROATIAN} "InfraRecorder Jezgrene Datoteke (obavezne)" LangString NAME_SecStartShortcut ${LANG_CROATIAN} "Start Meni Precaci" LangString NAME_SecDeskShortcut ${LANG_CROATIAN} "Desktop Precac" LangString NAME_SecQuickShortcut ${LANG_CROATIAN} "Quick Launch Precac" LangString NAME_SecLang ${LANG_CROATIAN} "Datoteke Jezika" LangString DESC_SecCore ${LANG_CROATIAN} "Jezgrene datoteke nune za upotrebu InfraRecorder." LangString DESC_SecStartShortcut ${LANG_CROATIAN} "Dodaje ikoneu Start meni radi lakeg pokretanja." LangString DESC_SecDeskShortcut ${LANG_CROATIAN} "Dodaje ikonu na va desktop." LangString DESC_SecQuickShortcut ${LANG_CROATIAN} "Dodaje ikonu u va Quick Launch liniju." LangString DESC_SecLang ${LANG_CROATIAN} "Datoteke jezika koritene za razlicite prijevode InfraRecorder-a." ; Language strings (Czech) LangString NAME_SecCore ${LANG_CZECH} "Zkladn soubory InfraRecorderu (nezbytn)" LangString NAME_SecStartShortcut ${LANG_CZECH} "Zstupci v nabdce Start" LangString NAME_SecDeskShortcut ${LANG_CZECH} "Zstupce na Ploe" LangString NAME_SecQuickShortcut ${LANG_CZECH} "Zstupce v panelu Snadn sputn" LangString NAME_SecLang ${LANG_CZECH} "Jazykov soubory" LangString DESC_SecCore ${LANG_CZECH} "Zkladn soubory potebn ke sputn InfraRecorderu." LangString DESC_SecStartShortcut ${LANG_CZECH} "Pid ikony do nabdky Start." LangString DESC_SecDeskShortcut ${LANG_CZECH} "Pid ikonu na Plochu." LangString DESC_SecQuickShortcut ${LANG_CZECH} "Pid ikonu do panelu Snadnho sputn." LangString DESC_SecLang ${LANG_CZECH} "Jazykov soubory zajiujc InfraRecorderu podporu rznch jazyk." ; Language strings (Danish) LangString NAME_SecCore ${LANG_DANISH} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_DANISH} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_DANISH} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_DANISH} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_DANISH} "Language Files" LangString DESC_SecCore ${LANG_DANISH} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_DANISH} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_DANISH} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_DANISH} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_DANISH} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Dutch) LangString NAME_SecCore ${LANG_DUTCH} "InfraRecorder essentile bestanden (benodigd)" LangString NAME_SecStartShortcut ${LANG_DUTCH} "Start Menu snelkoppelingen" LangString NAME_SecDeskShortcut ${LANG_DUTCH} "Bureaublad snelkoppeling" LangString NAME_SecQuickShortcut ${LANG_DUTCH} "Snel starten snelkoppeling" LangString NAME_SecLang ${LANG_DUTCH} "Taal bestanden" LangString DESC_SecCore ${LANG_DUTCH} "De essentile bestanden zijn nodig om InfraRecorder te kunnen gebruiken." LangString DESC_SecStartShortcut ${LANG_DUTCH} "Voegt pictogrammen toe aan het start menu voor snelle toegang." LangString DESC_SecDeskShortcut ${LANG_DUTCH} "Voegt een pictogram op het bureaublad toe." LangString DESC_SecQuickShortcut ${LANG_DUTCH} "Voegt een pictogram toe aan Snel starten op de taakbalk." LangString DESC_SecLang ${LANG_DUTCH} "Taal bestanden gebruikt voor ondersteuning van verschillende talen in InfraRecorder." ; Language strings (English) LangString NAME_SecCore ${LANG_ENGLISH} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_ENGLISH} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_ENGLISH} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_ENGLISH} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_ENGLISH} "Language Files" LangString DESC_SecCore ${LANG_ENGLISH} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_ENGLISH} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_ENGLISH} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_ENGLISH} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_ENGLISH} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Estonian) LangString NAME_SecCore ${LANG_ESTONIAN} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_ESTONIAN} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_ESTONIAN} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_ESTONIAN} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_ESTONIAN} "Language Files" LangString DESC_SecCore ${LANG_ESTONIAN} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_ESTONIAN} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_ESTONIAN} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_ESTONIAN} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_ESTONIAN} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Farsi) LangString NAME_SecCore ${LANG_FARSI} "( ј(" LangString NAME_SecStartShortcut ${LANG_FARSI} " " LangString NAME_SecDeskShortcut ${LANG_FARSI} " Ҙ" LangString NAME_SecQuickShortcut ${LANG_FARSI} " " LangString NAME_SecLang ${LANG_FARSI} " " LangString DESC_SecCore ${LANG_FARSI} " ј " LangString DESC_SecStartShortcut ${LANG_FARSI} " " LangString DESC_SecDeskShortcut ${LANG_FARSI} " Ҙ" LangString DESC_SecQuickShortcut ${LANG_FARSI} " " LangString DESC_SecLang ${LANG_FARSI} " ј " ; Language strings (Finnish) LangString NAME_SecCore ${LANG_FINNISH} "InfraRecorderin perustiedosto (pakollinen)" LangString NAME_SecStartShortcut ${LANG_FINNISH} "Kynnistvalikon pikakuvakkeet" LangString NAME_SecDeskShortcut ${LANG_FINNISH} "Typydn pikakuvake" LangString NAME_SecQuickShortcut ${LANG_FINNISH} "Pikakynnistyspalkin kuvake" LangString NAME_SecLang ${LANG_FINNISH} "Kielitiedostot" LangString DESC_SecCore ${LANG_FINNISH} "InfraRecorder'in kyttmiseen tarvittavat keskeiset tiedostot." LangString DESC_SecStartShortcut ${LANG_FINNISH} "Lis kuvakkeet Kynnist-valikkoon kytn helpottamiseksi." LangString DESC_SecDeskShortcut ${LANG_FINNISH} "Lis kuvake typydlle." LangString DESC_SecQuickShortcut ${LANG_FINNISH} "Lis kuvake pikakynnistyspalkkiin." LangString DESC_SecLang ${LANG_FINNISH} "Kielitiedostojen avulla InfraRecorderia voidaan kytt eri kielill." ; Language strings (French) LangString NAME_SecCore ${LANG_FRENCH} "Fichiers requis pour InfraRecorder" LangString NAME_SecStartShortcut ${LANG_FRENCH} "Raccourcis dans le Menu Dmarrer" LangString NAME_SecDeskShortcut ${LANG_FRENCH} "Raccourcis sur le Bureau" LangString NAME_SecQuickShortcut ${LANG_FRENCH} "Raccourci pour la barre de lancement rapide" LangString NAME_SecLang ${LANG_FRENCH} "Fichiers de Langues" LangString DESC_SecCore ${LANG_FRENCH} "Fichier requis pour le fonctionnement d'InfraRecorder." LangString DESC_SecStartShortcut ${LANG_FRENCH} "Ajouter des icones votre Menu Dmarrer pour un accs simplifi." LangString DESC_SecDeskShortcut ${LANG_FRENCH} "Ajouter un icone sur le Bureau." LangString DESC_SecQuickShortcut ${LANG_FRENCH} "Ajouter un icone votre barre de lancement rapide." LangString DESC_SecLang ${LANG_FRENCH} "Fichiers de langues ncessaires pour la traduction d'InfraRecorder." ; Language strings (Galician) LangString NAME_SecCore ${LANG_GALICIAN} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_GALICIAN} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_GALICIAN} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_GALICIAN} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_GALICIAN} "Language Files" LangString DESC_SecCore ${LANG_GALICIAN} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_GALICIAN} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_GALICIAN} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_GALICIAN} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_GALICIAN} "Language files used for supporting different languages in InfraRecorder." ; Language strings (German) LangString NAME_SecCore ${LANG_GERMAN} "InfraRecorder Programmdateien (notwendig)" LangString NAME_SecStartShortcut ${LANG_GERMAN} "Startmen-Eintrge" LangString NAME_SecDeskShortcut ${LANG_GERMAN} "Desktop-Eintrag" LangString NAME_SecQuickShortcut ${LANG_GERMAN} "Schnellstart-Eintrag" LangString NAME_SecLang ${LANG_GERMAN} "Zustzliche Sprachen" LangString DESC_SecCore ${LANG_GERMAN} "Alle bentigten Programmdateien fr den Einsatz von InfraRecorder." LangString DESC_SecStartShortcut ${LANG_GERMAN} "Fr leichten Zugriff Symbole zum Startmen hinzufgen." LangString DESC_SecDeskShortcut ${LANG_GERMAN} "Symbol auf dem Desktop erstellen." LangString DESC_SecQuickShortcut ${LANG_GERMAN} "Symbol auf Schnellstartleiste erstellen." LangString DESC_SecLang ${LANG_GERMAN} "Weitere Sprachdateien fr den mehrsprachigen Betrieb von InfraRecorder hinzufgen." ; Language strings (Georgian) LangString NAME_SecCore ${LANG_GEORGIAN} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_GEORGIAN} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_GEORGIAN} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_GEORGIAN} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_GEORGIAN} "Language Files" LangString DESC_SecCore ${LANG_GEORGIAN} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_GEORGIAN} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_GEORGIAN} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_GEORGIAN} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_GEORGIAN} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Greek) LangString NAME_SecCore ${LANG_GREEK} " InfraRecorder ()" LangString NAME_SecStartShortcut ${LANG_GREEK} " " LangString NAME_SecDeskShortcut ${LANG_GREEK} " " LangString NAME_SecQuickShortcut ${LANG_GREEK} " " LangString NAME_SecLang ${LANG_GREEK} " " LangString DESC_SecCore ${LANG_GREEK} " InfraRecorder." LangString DESC_SecStartShortcut ${LANG_GREEK} " ." LangString DESC_SecDeskShortcut ${LANG_GREEK} " ." LangString DESC_SecQuickShortcut ${LANG_GREEK} " ." LangString DESC_SecLang ${LANG_GREEK} " InfraRecorder." ; Language strings (Hebrew) LangString NAME_SecCore ${LANG_HEBREW} "Infra Recorder (required)" LangString NAME_SecStartShortcut ${LANG_HEBREW} " " LangString NAME_SecDeskShortcut ${LANG_HEBREW} " " LangString NAME_SecQuickShortcut ${LANG_HEBREW} " " LangString NAME_SecLang ${LANG_HEBREW} " " LangString DESC_SecCore ${LANG_HEBREW} " ." LangString DESC_SecStartShortcut ${LANG_HEBREW} " ." LangString DESC_SecDeskShortcut ${LANG_HEBREW} " ." LangString DESC_SecQuickShortcut ${LANG_HEBREW} " ." LangString DESC_SecLang ${LANG_HEBREW} " ." ; Language strings (Hungarian) LangString NAME_SecCore ${LANG_HUNGARIAN} "InfraRecorder Programfjlok (szksges)" LangString NAME_SecStartShortcut ${LANG_HUNGARIAN} "Start Men Parancsikonok" LangString NAME_SecDeskShortcut ${LANG_HUNGARIAN} "Asztali Parancsikon" LangString NAME_SecQuickShortcut ${LANG_HUNGARIAN} "Gyorsindt Parancsikon" LangString NAME_SecLang ${LANG_HUNGARIAN} "Nyelvi Fjlok" LangString DESC_SecCore ${LANG_HUNGARIAN} "A programfjlok szksgesek az InfraRecorder hasznlathoz." LangString DESC_SecStartShortcut ${LANG_HUNGARIAN} "Ikonok hozzadsa a start menhz a gyorsabb elrs rdekben." LangString DESC_SecDeskShortcut ${LANG_HUNGARIAN} "Ikon elhelyezse az asztalra." LangString DESC_SecQuickShortcut ${LANG_HUNGARIAN} "Ikon elhelyezse a gyorsindt pulton." LangString DESC_SecLang ${LANG_HUNGARIAN} "A nyelvi fjlok segtsgvel klnbz nyelveken hasznlhatja az InfraRecordert." ; Language strings (Indonesian) LangString NAME_SecCore ${LANG_INDONESIAN} "Berkas Inti InfraRecorder (dibutuhkan)" LangString NAME_SecStartShortcut ${LANG_INDONESIAN} "Jalan Pintas Menu Start" LangString NAME_SecDeskShortcut ${LANG_INDONESIAN} "Jalan Pintas Destop" LangString NAME_SecQuickShortcut ${LANG_INDONESIAN} "Jalan Pintas Luncur Cepat" LangString NAME_SecLang ${LANG_INDONESIAN} "Berkas Bahasa" LangString DESC_SecCore ${LANG_INDONESIAN} "Berkas inti yang dibutuhkan untuk menggunakan InfraRecorder." LangString DESC_SecStartShortcut ${LANG_INDONESIAN} "Tambah ikon ke menu start anda untuk kemudahan akses." LangString DESC_SecDeskShortcut ${LANG_INDONESIAN} "Tambah ikon ke destop anda." LangString DESC_SecQuickShortcut ${LANG_INDONESIAN} "Tambah ikon ke batang luncur cepat anda." LangString DESC_SecLang ${LANG_INDONESIAN} "Berkas bahasa yang digunakan untuk dukungan bahasa yang berbeda di InfraRecorder." ; Language strings (Italian) LangString NAME_SecCore ${LANG_ITALIAN} "File del programma InfraRecorder (Necessari)" LangString NAME_SecStartShortcut ${LANG_ITALIAN} "Collegamenti del menu' avvio" LangString NAME_SecDeskShortcut ${LANG_ITALIAN} "Icona sul desktop" LangString NAME_SecQuickShortcut ${LANG_ITALIAN} "Icona in avvio veloce" LangString NAME_SecLang ${LANG_ITALIAN} "File per le lingue" LangString DESC_SecCore ${LANG_ITALIAN} "I file del programma InfraRecorder." LangString DESC_SecStartShortcut ${LANG_ITALIAN} "Aggiunge le icone del programma al menu avvio per un comodo accesso." LangString DESC_SecDeskShortcut ${LANG_ITALIAN} "Aggiunge una icona sul desktop." LangString DESC_SecQuickShortcut ${LANG_ITALIAN} "Aggiunge una icona alla barra di avvio veloce." LangString DESC_SecLang ${LANG_ITALIAN} "File usati da InfraRecorder per il supporto delle lingue." ; Language strings (Japanese) LangString NAME_SecCore ${LANG_JAPANESE} "InfraRecorder {̃t@C (K{)" LangString NAME_SecStartShortcut ${LANG_JAPANESE} "[X^[g] j[ V[gJbg" LangString NAME_SecDeskShortcut ${LANG_JAPANESE} "fXNgbv V[gJbg" LangString NAME_SecQuickShortcut ${LANG_JAPANESE} "[NCbNN] V[gJbg" LangString NAME_SecLang ${LANG_JAPANESE} "t@C" LangString DESC_SecCore ${LANG_JAPANESE} "{̃t@C InfraRecorder gp̂ɕKvłB" LangString DESC_SecStartShortcut ${LANG_JAPANESE} "ȒPȃANZX̂߂ɃACRg [X^[g] j[ɒlj܂B" LangString DESC_SecDeskShortcut ${LANG_JAPANESE} "ACRg̃fXNgbvɒlj܂B" LangString DESC_SecQuickShortcut ${LANG_JAPANESE} "ACRg [NCbNN] o[ɒlj܂B" LangString DESC_SecLang ${LANG_JAPANESE} "t@C InfraRecorder قȂŃT|[ĝɎgp܂B" ; Language strings (Korean) LangString NAME_SecCore ${LANG_KOREAN} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_KOREAN} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_KOREAN} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_KOREAN} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_KOREAN} "Language Files" LangString DESC_SecCore ${LANG_KOREAN} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_KOREAN} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_KOREAN} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_KOREAN} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_KOREAN} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Latvian) LangString NAME_SecCore ${LANG_LATVIAN} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_LATVIAN} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_LATVIAN} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_LATVIAN} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_LATVIAN} "Language Files" LangString DESC_SecCore ${LANG_LATVIAN} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_LATVIAN} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_LATVIAN} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_LATVIAN} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_LATVIAN} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Lithuanian) LangString NAME_SecCore ${LANG_LITHUANIAN} "InfraRecorder pagrindiniai failai (btini)" LangString NAME_SecStartShortcut ${LANG_LITHUANIAN} "Start Menu nuorodos" LangString NAME_SecDeskShortcut ${LANG_LITHUANIAN} "Darbastalio nuoroda" LangString NAME_SecQuickShortcut ${LANG_LITHUANIAN} "Greito paleidimo nuoroda" LangString NAME_SecLang ${LANG_LITHUANIAN} "Kalbos failai" LangString DESC_SecCore ${LANG_LITHUANIAN} "Pagrindiniai failai bti norint naudotis InfraRecorder." LangString DESC_SecStartShortcut ${LANG_LITHUANIAN} "Sukuria ikonas start meniu greitam prijimui." LangString DESC_SecDeskShortcut ${LANG_LITHUANIAN} "Sukuria ikon ant darbastalio." LangString DESC_SecQuickShortcut ${LANG_LITHUANIAN} "Sukuria ikon greito paleidimo juost." LangString DESC_SecLang ${LANG_LITHUANIAN} "Kalbos failai reikalingi norint kad InfraRecorder vartotojo ssaja dirbt skirtingomis kalbomis." ; Language strings (Macedonian) LangString NAME_SecCore ${LANG_MACEDONIAN} " InfraRecorder ()" LangString NAME_SecStartShortcut ${LANG_MACEDONIAN} " " LangString NAME_SecDeskShortcut ${LANG_MACEDONIAN} " " LangString NAME_SecQuickShortcut ${LANG_MACEDONIAN} " " LangString NAME_SecLang ${LANG_MACEDONIAN} " " LangString DESC_SecCore ${LANG_MACEDONIAN} " InfraRecorder." LangString DESC_SecStartShortcut ${LANG_MACEDONIAN} " ." LangString DESC_SecDeskShortcut ${LANG_MACEDONIAN} " ." LangString DESC_SecQuickShortcut ${LANG_MACEDONIAN} " ." LangString DESC_SecLang ${LANG_MACEDONIAN} " InfraRecorder." ; Language strings (Norwegian) LangString NAME_SecCore ${LANG_NORWEGIAN} "InfraRecorder kjernefiler (obligatorisk)" LangString NAME_SecStartShortcut ${LANG_NORWEGIAN} "Snarvei i startmenyen" LangString NAME_SecDeskShortcut ${LANG_NORWEGIAN} "Snarvei p skrivebordet" LangString NAME_SecQuickShortcut ${LANG_NORWEGIAN} "Snarvei p hurtigstartlinjen" LangString NAME_SecLang ${LANG_NORWEGIAN} "Sprkfiler" LangString DESC_SecCore ${LANG_NORWEGIAN} "Installerer kjernefiler som kreves for kjre InfraRecorder" LangString DESC_SecStartShortcut ${LANG_NORWEGIAN} "Oppretter programmappe for InfraRecorder i startmenyen" LangString DESC_SecDeskShortcut ${LANG_NORWEGIAN} "Oppretter programikon for InfraRecorder p skrivebordet" LangString DESC_SecQuickShortcut ${LANG_NORWEGIAN} "Oppretter programikon for InfraRecorder p hurtigstartlinjen" LangString DESC_SecLang ${LANG_NORWEGIAN} "Installerer sprkfiler som tillater bruk av ulike sprk i InfraRecorder" ; Language strings (Polish) LangString NAME_SecCore ${LANG_POLISH} "Gwne pliki InfraRecorder (wymagane)" LangString NAME_SecStartShortcut ${LANG_POLISH} "Skrty menu Start" LangString NAME_SecDeskShortcut ${LANG_POLISH} "Skrty na pulpicie" LangString NAME_SecQuickShortcut ${LANG_POLISH} "Skrty w szybkim uruchamianiu" LangString NAME_SecLang ${LANG_POLISH} "Pliki jzykowe" LangString DESC_SecCore ${LANG_POLISH} "Gwne pliki wymagane przez InfraRecorder." LangString DESC_SecStartShortcut ${LANG_POLISH} "Dodaje ikony w menu Start." LangString DESC_SecDeskShortcut ${LANG_POLISH} "Dodaje ikon na pulpicie." LangString DESC_SecQuickShortcut ${LANG_POLISH} "Dodaje ikon w pasku szybkiego uruchamiania." LangString DESC_SecLang ${LANG_POLISH} "Pliki jzykowe dla obsugi innych jzykw w InfraRecorder." ; Language strings (Portuguese) LangString NAME_SecCore ${LANG_PORTUGUESE} "Ficheiros Base do 'InfraRecorder' (obrigatorios)" LangString NAME_SecStartShortcut ${LANG_PORTUGUESE} "Atalhos do Menu de Programas" LangString NAME_SecDeskShortcut ${LANG_PORTUGUESE} "Atalho do Ambiente de Trabalho" LangString NAME_SecQuickShortcut ${LANG_PORTUGUESE} "Atalho da Barra de Iniciacao Rapida" LangString NAME_SecLang ${LANG_PORTUGUESE} "Ficheiros de Linguas" LangString DESC_SecCore ${LANG_PORTUGUESE} "Os ficheiros base obrigatorios para correr o 'InfraRecorder'." LangString DESC_SecStartShortcut ${LANG_PORTUGUESE} "Adiciona 'icons' ao menu de programas para um melhor acesso." LangString DESC_SecDeskShortcut ${LANG_PORTUGUESE} "Adiciona um 'icon' ao ambiente de trabalho." LangString DESC_SecQuickShortcut ${LANG_PORTUGUESE} "Adiciona um 'icon' a barra de iniciacao rapida." LangString DESC_SecLang ${LANG_PORTUGUESE} "Ficheiros de linguas usados para suportar o 'InfraRecorder' em modo multi-lingual." ; Language strings (Brazilian Portuguese) LangString NAME_SecCore ${LANG_PORTUGUESEBR} "Arquivos de Ncleo do InfraRecorder (requeridos)" LangString NAME_SecStartShortcut ${LANG_PORTUGUESEBR} "Atalhos do Menu Iniciar" LangString NAME_SecDeskShortcut ${LANG_PORTUGUESEBR} "Atalho do Desktop" LangString NAME_SecQuickShortcut ${LANG_PORTUGUESEBR} "Atalho da Barra de Inicializao Rpida" LangString NAME_SecLang ${LANG_PORTUGUESEBR} "Arquivos de Linguagem" LangString DESC_SecCore ${LANG_PORTUGUESEBR} "Os arquivos de ncleo requeridos pelo InfraRecorder" LangString DESC_SecStartShortcut ${LANG_PORTUGUESEBR} "Adiciona cones ao menu iniciar para acesso fcil" LangString DESC_SecDeskShortcut ${LANG_PORTUGUESEBR} "Adicionar um cone no Desktop" LangString DESC_SecQuickShortcut ${LANG_PORTUGUESEBR} "Adicionar um cone na Barra de Inicializao Rpida" LangString DESC_SecLang ${LANG_PORTUGUESEBR} "Arquivos de linguagem utilizados para o suporte multilnge no InfraRecorder" ; Language strings (Romanian) LangString NAME_SecCore ${LANG_ROMANIAN} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_ROMANIAN} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_ROMANIAN} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_ROMANIAN} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_ROMANIAN} "Language Files" LangString DESC_SecCore ${LANG_ROMANIAN} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_ROMANIAN} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_ROMANIAN} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_ROMANIAN} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_ROMANIAN} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Russian) LangString NAME_SecCore ${LANG_RUSSIAN} " InfraRecorder ()" LangString NAME_SecStartShortcut ${LANG_RUSSIAN} " " LangString NAME_SecDeskShortcut ${LANG_RUSSIAN} " " LangString NAME_SecQuickShortcut ${LANG_RUSSIAN} " " LangString NAME_SecLang ${LANG_RUSSIAN} " " LangString DESC_SecCore ${LANG_RUSSIAN} " , InfraRecorder." LangString DESC_SecStartShortcut ${LANG_RUSSIAN} " ." LangString DESC_SecDeskShortcut ${LANG_RUSSIAN} " ." LangString DESC_SecQuickShortcut ${LANG_RUSSIAN} " ." LangString DESC_SecLang ${LANG_RUSSIAN} " InfraRecorder." ; Language strings (Cyrillic Serbian) LangString NAME_SecCore ${LANG_SERBIAN} "InfraRecorder ()" LangString NAME_SecStartShortcut ${LANG_SERBIAN} " " LangString NAME_SecDeskShortcut ${LANG_SERBIAN} " " LangString NAME_SecQuickShortcut ${LANG_SERBIAN} " " LangString NAME_SecLang ${LANG_SERBIAN} " " LangString DESC_SecCore ${LANG_SERBIAN} " InfraRecorder-." LangString DESC_SecStartShortcut ${LANG_SERBIAN} " ." LangString DESC_SecDeskShortcut ${LANG_SERBIAN} " ." LangString DESC_SecQuickShortcut ${LANG_SERBIAN} " ." LangString DESC_SecLang ${LANG_SERBIAN} " InfraRecorder." ; Language strings (Latin Serbian) LangString NAME_SecCore ${LANG_SERBIANLATIN} "InfraRecorder datoteke (potrebno)" LangString NAME_SecStartShortcut ${LANG_SERBIANLATIN} "Preica Start menija" LangString NAME_SecDeskShortcut ${LANG_SERBIANLATIN} "Preica radne povrine" LangString NAME_SecQuickShortcut ${LANG_SERBIANLATIN} "Preica brzog pokretanja" LangString NAME_SecLang ${LANG_SERBIANLATIN} "Jezike datoteke" LangString DESC_SecCore ${LANG_SERBIANLATIN} "Datoteke za rad InfraRecorder-a." LangString DESC_SecStartShortcut ${LANG_SERBIANLATIN} "Dodaj ikone u start meniju za laki pristup." LangString DESC_SecDeskShortcut ${LANG_SERBIANLATIN} "Dodaj ikonu na radnoj povrini." LangString DESC_SecQuickShortcut ${LANG_SERBIANLATIN} "Dodaj ikonu na traku brzog pokretanja." LangString DESC_SecLang ${LANG_SERBIANLATIN} "Jezike datoteke za InfraRecorder." ; Language strings (Slovak) LangString NAME_SecCore ${LANG_SLOVAK} "Zkladn sbory InfraRecorderu (nutn)" LangString NAME_SecStartShortcut ${LANG_SLOVAK} "Odkazy v menu tart" LangString NAME_SecDeskShortcut ${LANG_SLOVAK} "Odkaz na Plochu" LangString NAME_SecQuickShortcut ${LANG_SLOVAK} "Odkaz do panelu Rchle spustenie" LangString NAME_SecLang ${LANG_SLOVAK} "Sbory jazykov" LangString DESC_SecCore ${LANG_SLOVAK} "Zkladn sbory nutn na pouvanie InfraRecorderu" LangString DESC_SecStartShortcut ${LANG_SLOVAK} "Prid ikony do ponuky tart pre zjednodunie prstupu." LangString DESC_SecDeskShortcut ${LANG_SLOVAK} "Prid ikonu na Plochu" LangString DESC_SecQuickShortcut ${LANG_SLOVAK} "Prid ikonu do Vho panelu Rchle spustenie." LangString DESC_SecLang ${LANG_SLOVAK} "Sbory jazykov, pouit pre podporu rznych jazykov InfraRecorderu" ; Language strings (Slovenian) LangString NAME_SecCore ${LANG_SLOVENIAN} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_SLOVENIAN} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_SLOVENIAN} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_SLOVENIAN} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_SLOVENIAN} "Language Files" LangString DESC_SecCore ${LANG_SLOVENIAN} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_SLOVENIAN} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_SLOVENIAN} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_SLOVENIAN} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_SLOVENIAN} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Simplified Chinese) LangString NAME_SecCore ${LANG_SIMPCHINESE} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_SIMPCHINESE} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_SIMPCHINESE} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_SIMPCHINESE} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_SIMPCHINESE} "Language Files" LangString DESC_SecCore ${LANG_SIMPCHINESE} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_SIMPCHINESE} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_SIMPCHINESE} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_SIMPCHINESE} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_SIMPCHINESE} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Spanish) LangString NAME_SecCore ${LANG_SPANISH} "Ncleo de InfraRecorder (requerido)" LangString NAME_SecStartShortcut ${LANG_SPANISH} "Accesos directos en men de inicio" LangString NAME_SecDeskShortcut ${LANG_SPANISH} "Acceso directo en el escritorio" LangString NAME_SecQuickShortcut ${LANG_SPANISH} "Acceso directo en inicio rpido" LangString NAME_SecLang ${LANG_SPANISH} "Archivos de idiomas" LangString DESC_SecCore ${LANG_SPANISH} "El ncleo de archivos necesario para usar InfraRecorder." LangString DESC_SecStartShortcut ${LANG_SPANISH} "Agrega iconos a su men de inicio para acceder fcilmente." LangString DESC_SecDeskShortcut ${LANG_SPANISH} "Agrega un icono a su escritorio." LangString DESC_SecQuickShortcut ${LANG_SPANISH} "Agrega un icono a su barra de inicio rpido." LangString DESC_SecLang ${LANG_SPANISH} "Archivos usados para soporte de diferentes idiomas en InfraRecorder." ; Language strings (Swedish) LangString NAME_SecCore ${LANG_SWEDISH} "InfraRecorder huvudfiler (krvs)" LangString NAME_SecStartShortcut ${LANG_SWEDISH} "Startmeny genvgar" LangString NAME_SecDeskShortcut ${LANG_SWEDISH} "Skrivbord genvg" LangString NAME_SecQuickShortcut ${LANG_SWEDISH} "Snabbstart genvg" LangString NAME_SecLang ${LANG_SWEDISH} "Sprkfiler" LangString DESC_SecCore ${LANG_SWEDISH} "Huvudfilerna som krvs fr att anvnda InfraRecorder." LangString DESC_SecStartShortcut ${LANG_SWEDISH} "Lgger till ikoner p din startmeny." LangString DESC_SecDeskShortcut ${LANG_SWEDISH} "Lgger till en ikon p ditt skrivbord." LangString DESC_SecQuickShortcut ${LANG_SWEDISH} "Lgger till en ikon p snabbstartfltet." LangString DESC_SecLang ${LANG_SWEDISH} "Sprkfiler som anvnds fr att stdja olika sprk i InfraRecorder." ; Language strings (Thai) LangString NAME_SecCore ${LANG_THAI} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_THAI} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_THAI} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_THAI} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_THAI} "Language Files" LangString DESC_SecCore ${LANG_THAI} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_THAI} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_THAI} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_THAI} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_THAI} "Language files used for supporting different languages in InfraRecorder." ; Language strings (Traditional Chinese) LangString NAME_SecCore ${LANG_TRADCHINESE} "InfraRecorder֤ɮ(nw)" LangString NAME_SecStartShortcut ${LANG_TRADCHINESE} "}l\|" LangString NAME_SecDeskShortcut ${LANG_TRADCHINESE} "ୱ|" LangString NAME_SecQuickShortcut ${LANG_TRADCHINESE} "ֳtҰʼb" LangString NAME_SecLang ${LANG_TRADCHINESE} "yɮ" LangString DESC_SecCore ${LANG_TRADCHINESE} " InfraRecorder һݭn֤ɮ" LangString DESC_SecStartShortcut ${LANG_TRADCHINESE} "W[ϥܦܶ}l\" LangString DESC_SecDeskShortcut ${LANG_TRADCHINESE} "W[ϥܦܮୱ" LangString DESC_SecQuickShortcut ${LANG_TRADCHINESE} "W[ϥܦܧֳtҰ" LangString DESC_SecLang ${LANG_TRADCHINESE} " InfraRecorder 䴩Pay" ; Language strings (Turkish) LangString NAME_SecCore ${LANG_TURKISH} "InfraRecorder Ana Dosyalar (Gerekli)" LangString NAME_SecStartShortcut ${LANG_TURKISH} "Balat Mens Ksayollar" LangString NAME_SecDeskShortcut ${LANG_TURKISH} "Masast Ksayolu" LangString NAME_SecQuickShortcut ${LANG_TURKISH} "Hzl Balat Ksayolu" LangString NAME_SecLang ${LANG_TURKISH} "Dil Dosyalar" LangString DESC_SecCore ${LANG_TURKISH} "InfraRecorder' kullanabilmek iin gereken ana dosyalar." LangString DESC_SecStartShortcut ${LANG_TURKISH} "Balat Mensne programa hzl eriebilmek iin simgeleri ekler." LangString DESC_SecDeskShortcut ${LANG_TURKISH} "Masastne simge ekler." LangString DESC_SecQuickShortcut ${LANG_TURKISH} "Hzl Balata simge ekler" LangString DESC_SecLang ${LANG_TURKISH} "InfraRecorder' farkl dillerde kullanabilmek iin dil dosyalar." ; Language strings (Ukrainian) LangString NAME_SecCore ${LANG_UKRAINIAN} " InfraRecorder ()" LangString NAME_SecStartShortcut ${LANG_UKRAINIAN} " ''" LangString NAME_SecDeskShortcut ${LANG_UKRAINIAN} " " LangString NAME_SecQuickShortcut ${LANG_UKRAINIAN} " " LangString NAME_SecLang ${LANG_UKRAINIAN} " " LangString DESC_SecCore ${LANG_UKRAINIAN} " InfraRecorder." LangString DESC_SecStartShortcut ${LANG_UKRAINIAN} " '' ..." LangString DESC_SecDeskShortcut ${LANG_UKRAINIAN} " ." LangString DESC_SecQuickShortcut ${LANG_UKRAINIAN} " ." LangString DESC_SecLang ${LANG_UKRAINIAN} " InfraRecorder." ; Language strings (Vietnamese) LangString NAME_SecCore ${LANG_VIETNAMESE} "InfraRecorder Core Files (required)" LangString NAME_SecStartShortcut ${LANG_VIETNAMESE} "Start Menu Shortcuts" LangString NAME_SecDeskShortcut ${LANG_VIETNAMESE} "Desktop Shortcut" LangString NAME_SecQuickShortcut ${LANG_VIETNAMESE} "Quick Launch Shortcut" LangString NAME_SecLang ${LANG_VIETNAMESE} "Language Files" LangString DESC_SecCore ${LANG_VIETNAMESE} "The core files required to use InfraRecorder." LangString DESC_SecStartShortcut ${LANG_VIETNAMESE} "Adds icons to your start menu for easy access." LangString DESC_SecDeskShortcut ${LANG_VIETNAMESE} "Adds an icon to your desktop." LangString DESC_SecQuickShortcut ${LANG_VIETNAMESE} "Adds an icon to your quick launch bar." LangString DESC_SecLang ${LANG_VIETNAMESE} "Language files used for supporting different languages in InfraRecorder." ;-------------------------------- ; Installer Sections Section $(NAME_SecCore) SecCore SectionIn 1 2 RO SetOutPath "$INSTDIR" File "..\..\readme.txt" File "..\..\license.txt" File "..\..\doc\english\infrarecorder.chm" File "..\..\bin\win32\release\infrarecorder.exe" File "..\..\bin\win32\release\shell.dll" File "..\..\dep\smoke\win32\smoke.exe" SetOutPath "$INSTDIR\codecs" ;File "..\..\bin\win32\release\codecs\wave.irc" File "..\..\bin\win32\release\codecs\sndfile.irc" File "..\..\dep\libsndfile\win32\libsndfile-1.dll" File "..\..\bin\win32\release\codecs\wma.irc" File "..\..\bin\win32\release\codecs\vorbis.irc" !ifdef CDRKIT SetOutPath "$INSTDIR\cdrkit" File "..\..\dep\cdrkit\icedax.exe" File "..\..\dep\cdrkit\wodim.exe" File "..\..\dep\cdrkit\cygwin1.dll" File "..\..\dep\cdrkit\readom.exe" File "..\..\dep\cdrkit\COPYING" !else SetOutPath "$INSTDIR\cdrtools" File "..\..\dep\cdrtools\cdda2wav.exe" File "..\..\dep\cdrtools\cdrecord.exe" File "..\..\dep\cdrtools\cygwin1.dll" File "..\..\dep\cdrtools\readcd.exe" File "..\..\dep\cdrtools\COPYING" !endif ; Store installation folder. WriteRegStr HKCU "Software\InfraRecorder" "" $INSTDIR ; Create uninstaller. !ifndef INNER SetOutPath "$INSTDIR" ; Package the signed uninstaller. File $%TEMP%\uninstall.exe !endif ; Add an entry to Add/Remove Programs. WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\InfraRecorder" \ "DisplayName" "InfraRecorder" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\InfraRecorder" \ "Publisher" "Christian Kindahl" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\InfraRecorder" \ "UninstallString" "$\"$INSTDIR\uninstall.exe$\"" WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\InfraRecorder" \ "DisplayIcon" "$INSTDIR\infrarecorder.exe" SectionEnd Section $(NAME_SecStartShortcut) SecStartShortcut SectionIn 1 ; Start menu shortcuts. CreateDirectory "$SMPROGRAMS\InfraRecorder" CreateShortCut "$SMPROGRAMS\InfraRecorder\InfraRecorder.lnk" "$INSTDIR\infrarecorder.exe" CreateShortCut "$SMPROGRAMS\InfraRecorder\InfraRecorder Help.lnk" "$INSTDIR\infrarecorder.chm" CreateShortCut "$SMPROGRAMS\InfraRecorder\Uninstall.lnk" "$INSTDIR\uninstall.exe" SectionEnd Section $(NAME_SecDeskShortcut) SecDeskShortcut SectionIn 1 CreateShortCut "$DESKTOP\InfraRecorder.lnk" "$INSTDIR\infrarecorder.exe" SectionEnd Section $(NAME_SecQuickShortcut) SecQuickShortcut SectionIn 1 ; Quick launch shortcut. CreateShortCut "$QUICKLAUNCH\InfraRecorder.lnk" "$INSTDIR\infrarecorder.exe" SectionEnd Section $(NAME_SecLang) SecLang SectionIn 1 SetOutPath "$INSTDIR\languages" File "..\..\etc\translations\software\albanian.irl" File "..\..\etc\translations\software\arabic.irl" File "..\..\etc\translations\software\armenian.irl" File "..\..\etc\translations\software\basque.irl" File "..\..\etc\translations\software\bosnian.irl" File "..\..\etc\translations\software\bulgarian.irl" File "..\..\etc\translations\software\catalan.irl" File "..\..\etc\translations\software\chinese-simplified.irl" File "..\..\etc\translations\software\chinese-traditional.irl" File "..\..\etc\translations\software\chuvash.irl" File "..\..\etc\translations\software\croatian.irl" File "..\..\etc\translations\software\czech.irl" File "..\..\etc\translations\software\danish.irl" File "..\..\etc\translations\software\dutch.irl" File "..\..\etc\translations\software\estonian.irl" File "..\..\etc\translations\software\farsi.irl" File "..\..\etc\translations\software\finnish.irl" File "..\..\etc\translations\software\french.irl" File "..\..\etc\translations\software\galician.irl" File "..\..\etc\translations\software\german.irl" File "..\..\etc\translations\software\georgian.irl" File "..\..\etc\translations\software\greek.irl" File "..\..\etc\translations\software\hebrew.irl" File "..\..\etc\translations\software\hungarian.irl" File "..\..\etc\translations\software\indonesian.irl" File "..\..\etc\translations\software\italian.irl" File "..\..\etc\translations\software\japanese.irl" File "..\..\etc\translations\software\korean.irl" File "..\..\etc\translations\software\latvian.irl" File "..\..\etc\translations\software\lithuanian.irl" File "..\..\etc\translations\software\macedonian.irl" File "..\..\etc\translations\software\norwegian.irl" File "..\..\etc\translations\software\polish.irl" File "..\..\etc\translations\software\portuguese.irl" File "..\..\etc\translations\software\portuguese-brazilian.irl" File "..\..\etc\translations\software\romanian.irl" File "..\..\etc\translations\software\russian.irl" File "..\..\etc\translations\software\serbian-cyrillic.irl" File "..\..\etc\translations\software\serbian-latin.irl" File "..\..\etc\translations\software\slovak.irl" File "..\..\etc\translations\software\slovenian.irl" File "..\..\etc\translations\software\spanish.irl" File "..\..\etc\translations\software\swedish.irl" File "..\..\etc\translations\software\thai.irl" File "..\..\etc\translations\software\turkish.irl" File "..\..\etc\translations\software\ukrainian.irl" File "..\..\etc\translations\software\valencian.irl" File "..\..\etc\translations\software\vietnamese.irl" File "..\..\etc\translations\help\czech.chm" File "..\..\etc\translations\help\french.chm" File "..\..\etc\translations\help\german.chm" File "..\..\etc\translations\help\russian.chm" File "..\..\etc\translations\help\thai.chm" File "..\..\etc\translations\help\turkish.chm" File "..\..\etc\translations\help\ukrainian.chm" ; Check if a language has been specified by the commandline. ; http://www.microsoft.com/globaldev/reference/oslocversion.mspx ; http://www.microsoft.com/globaldev/reference/lcid-all.mspx ${Switch} $1 ${case} "albanian" StrCpy $LANGUAGE ${LANG_ALBANIAN} ${break} ${case} "arabic" ; 1025 StrCpy $LANGUAGE ${LANG_ARABIC} ${break} ${case} "armenian" StrCpy $LANGUAGE ${LANG_ARMENIAN} ${break} ${case} "basque" ; 1069 StrCpy $LANGUAGE ${LANG_BASQUE} ${break} ${case} "bosnian" ; 5146 StrCpy $LANGUAGE ${LANG_BOSNIAN} ${break} ${case} "bulgarian" ; 1026 StrCpy $LANGUAGE ${LANG_BULGARIAN} ${break} ${case} "catalan" ; 1027 StrCpy $LANGUAGE ${LANG_CATALAN} ${break} ${Case} "simpchinese" ; 2052 StrCpy $LANGUAGE ${LANG_SIMPCHINESE} ${Break} ${Case} "tradchinese" ; 1028 StrCpy $LANGUAGE ${LANG_TRADCHINESE} ${Break} ${Case} "chuvash" StrCpy $LANGUAGE ${LANG_CHUVASH} ${Break} ${Case} "croatian" ; 1050 StrCpy $LANGUAGE ${LANG_CROATIAN} ${Break} ${case} "czech" ; 1029 StrCpy $LANGUAGE ${LANG_CZECH} ${break} ${case} "danish" ; 1030 StrCpy $LANGUAGE ${LANG_DANISH} ${break} ${Case} "dutch" ; 1043 StrCpy $LANGUAGE ${LANG_DUTCH} ${Break} ${Case} "english" ; 1033 StrCpy $LANGUAGE ${LANG_ENGLISH} ${Break} ${Case} "estonian" StrCpy $LANGUAGE ${LANG_ESTONIAN} ${Break} ${Case} "farsi" StrCpy $LANGUAGE ${LANG_FARSI} ${Break} ${Case} "finnish" ; 1035 StrCpy $LANGUAGE ${LANG_FINNISH} ${Break} ${Case} "french" ; 1036 StrCpy $LANGUAGE ${LANG_FRENCH} ${Break} ${Case} "galician" StrCpy $LANGUAGE ${LANG_GALICIAN} ${Break} ${Case} "german" ; 1031 StrCpy $LANGUAGE ${LANG_GERMAN} ${Break} ${Case} "georgian" StrCpy $LANGUAGE ${LANG_GEORGIAN} ${Break} ${Case} "greek" ; 1032 StrCpy $LANGUAGE ${LANG_GREEK} ${Break} ${Case} "hebrew" ; 1037 StrCpy $LANGUAGE ${LANG_HEBREW} ${Break} ${Case} "hungarian" ; 1038 StrCpy $LANGUAGE ${LANG_HUNGARIAN} ${Break} ${Case} "indonesian"; 1057 StrCpy $LANGUAGE ${LANG_INDONESIAN} ${Break} ${Case} "italian" ; 1040 StrCpy $LANGUAGE ${LANG_ITALIAN} ${Break} ${Case} "japanese" ; 1041 StrCpy $LANGUAGE ${LANG_JAPANESE} ${Break} ${Case} "korean" ; 1042 StrCpy $LANGUAGE ${LANG_KOREAN} ${Break} ${Case} "latvian" StrCpy $LANGUAGE ${LANG_LATVIAN} ${Break} ${Case} "lithuanian"; 1063 StrCpy $LANGUAGE ${LANG_LITHUANIAN} ${Break} ${Case} "macedonian" StrCpy $LANGUAGE ${LANG_MACEDONIAN} ${Break} ${Case} "norwegian"; 1044 StrCpy $LANGUAGE ${LANG_NORWEGIAN} ${Break} ${Case} "polish"; 1045 StrCpy $LANGUAGE ${LANG_POLISH} ${Break} ${Case} "portuguese"; 2070 StrCpy $LANGUAGE ${LANG_PORTUGUESE} ${Break} ${Case} "portuguesebr"; 1046 StrCpy $LANGUAGE ${LANG_PORTUGUESEBR} ${Break} ${Case} "romanian"; 1048 StrCpy $LANGUAGE ${LANG_ROMANIAN} ${Break} ${Case} "russian" ; 1049 StrCpy $LANGUAGE ${LANG_RUSSIAN} ${Break} ${Case} "serbian" ; 3098 StrCpy $LANGUAGE ${LANG_SERBIAN} ${Break} ${Case} "serbianlatin"; 2074 StrCpy $LANGUAGE ${LANG_SERBIANLATIN} ${Break} ${Case} "slovak" ; 1051 StrCpy $LANGUAGE ${LANG_SLOVAK} ${Break} ${Case} "slovenian" ; 1060 StrCpy $LANGUAGE ${LANG_SLOVENIAN} ${Break} ${Case} "spanish" ; 1034 StrCpy $LANGUAGE ${LANG_SPANISH} ${Break} ${Case} "swedish" ; 1053 StrCpy $LANGUAGE ${LANG_SWEDISH} ${Break} ${Case} "thai" ; 1054 StrCpy $LANGUAGE ${LANG_THAI} ${Break} ${Case} "turkish" ; 1055 StrCpy $LANGUAGE ${LANG_TURKISH} ${Break} ${Case} "ukrainian" ; 1058 StrCpy $LANGUAGE ${LANG_UKRAINIAN} ${Break} ${Case} "valencian" ; 1058 StrCpy $LANGUAGE ${LANG_VALENCIAN} ${Break} ${Case} "vietnamese" StrCpy $LANGUAGE ${LANG_VIETNAMESE} ${Break} ${EndSwitch} ; Calculate file name of the translation file. ; http://www.microsoft.com/globaldev/reference/oslocversion.mspx ; http://www.microsoft.com/globaldev/reference/lcid-all.mspx ${Switch} $LANGUAGE ${Case} ${LANG_ALBANIAN} StrCpy $0 "albanian.irl" ${Break} ${Case} ${LANG_ARABIC} ; 1025 StrCpy $0 "arabic.irl" ${Break} ${Case} ${LANG_ARMENIAN} StrCpy $0 "armenian.irl" ${Break} ${Case} ${LANG_BASQUE} ; 1069 StrCpy $0 "basque.irl" ${Break} ${Case} ${LANG_BOSNIAN} ; 5146 StrCpy $0 "bosnian.irl" ${Break} ${Case} ${LANG_BULGARIAN} ; 1026 StrCpy $0 "bulgarian.irl" ${Break} ${Case} ${LANG_CATALAN} ; 1027 StrCpy $0 "catalan.irl" ${Break} ${Case} ${LANG_SIMPCHINESE} ; 2052 StrCpy $0 "chinese-simplified.irl" ${Break} ${Case} ${LANG_TRADCHINESE} ; 1028 StrCpy $0 "chinese-traditional.irl" ${Break} ${Case} ${LANG_CHUVASH} StrCpy $0 "chuvash.irl" ${Break} ${Case} ${LANG_CROATIAN} ; 1050 StrCpy $0 "croatian.irl" ${Break} ${Case} ${LANG_CZECH} ; 1029 StrCpy $0 "czech.irl" ${Break} ${Case} ${LANG_DANISH} ; 1030 StrCpy $0 "danish.irl" ${Break} ${Case} ${LANG_DUTCH} ; 1043 StrCpy $0 "dutch.irl" ${Break} ${Case} ${LANG_ENGLISH} ; 1033 StrCpy $0 "" ${Break} ${Case} ${LANG_ESTONIAN} StrCpy $0 "estonian.irl" ${Break} ${Case} ${LANG_FARSI} StrCpy $0 "farsi.irl" ${Break} ${Case} ${LANG_FINNISH} ; 1035 StrCpy $0 "finnish.irl" ${Break} ${Case} ${LANG_FRENCH} ; 1036 StrCpy $0 "french.irl" ${Break} ${Case} ${LANG_GALICIAN} StrCpy $0 "galician.irl" ${Break} ${Case} ${LANG_GERMAN} ; 1031 StrCpy $0 "german.irl" ${Break} ${Case} ${LANG_GEORGIAN} StrCpy $0 "georgian.irl" ${Break} ${Case} ${LANG_GREEK} ; 1032 StrCpy $0 "greek.irl" ${Break} ${Case} ${LANG_HEBREW} ; 1037 StrCpy $0 "hebrew.irl" ${Break} ${Case} ${LANG_HUNGARIAN} ; 1038 StrCpy $0 "hungarian.irl" ${Break} ${Case} ${LANG_INDONESIAN} ; 1057 StrCpy $0 "indonesian.irl" ${Break} ${Case} ${LANG_ITALIAN} ; 1040 StrCpy $0 "italian.irl" ${Break} ${Case} ${LANG_JAPANESE} ; 1041 StrCpy $0 "japanese.irl" ${Break} ${Case} ${LANG_KOREAN} ; 1042 StrCpy $0 "korean.irl" ${Break} ${Case} ${LANG_LATVIAN} StrCpy $0 "latvian.irl" ${Break} ${Case} ${LANG_LITHUANIAN} ; 1063 StrCpy $0 "lithuanian.irl" ${Break} ${Case} ${LANG_MACEDONIAN} StrCpy $0 "macedonian.irl" ${Break} ${Case} ${LANG_NORWEGIAN} ; 1044 StrCpy $0 "norwegian.irl" ${Break} ${Case} ${LANG_POLISH} ; 1045 StrCpy $0 "polish.irl" ${Break} ${Case} ${LANG_PORTUGUESE} ; 2070 StrCpy $0 "portuguese.irl" ${Break} ${Case} ${LANG_PORTUGUESEBR} ; 1046 StrCpy $0 "portuguese-brazilian.irl" ${Break} ${Case} ${LANG_ROMANIAN} ; 1048 StrCpy $0 "romanian.irl" ${Break} ${Case} ${LANG_RUSSIAN} ; 1049 StrCpy $0 "russian.irl" ${Break} ${Case} ${LANG_SERBIAN} ; 3098 StrCpy $0 "serbian-cyrillic.irl" ${Break} ${Case} ${LANG_SERBIANLATIN} ; 2074 StrCpy $0 "serbian-latin.irl" ${Break} ${Case} ${LANG_SLOVAK} ; 1051 StrCpy $0 "slovak.irl" ${Break} ${Case} ${LANG_SLOVENIAN} ; 1060 StrCpy $0 "slovenian.irl" ${Break} ${Case} ${LANG_SPANISH} ; 1034 StrCpy $0 "spanish.irl" ${Break} ${Case} ${LANG_SWEDISH} ; 1053 StrCpy $0 "swedish.irl" ${Break} ${Case} ${LANG_THAI} ; 1054 StrCpy $0 "thai.irl" ${Break} ${Case} ${LANG_TURKISH} ; 1055 StrCpy $0 "turkish.irl" ${Break} ${Case} ${LANG_UKRAINIAN} ; 1058 StrCpy $0 "ukrainian.irl" ${Break} ${Case} ${LANG_VALENCIAN} StrCpy $0 "valencian.irl" ${Break} ${Case} ${LANG_VIETNAMESE} StrCpy $0 "vietnamese.irl" ${Break} ${EndSwitch} ; Create a configuration file with a preselected language file (if the ; selected language is not English). ${If} $0 != "" ir_plugin::CreateConfig "$INSTDIR\settings.xml" "$0" ${EndIf} SectionEnd ;-------------------------------- ; Description Macros ; Assign language strings to sections !insertmacro MUI_FUNCTION_DESCRIPTION_BEGIN !insertmacro MUI_DESCRIPTION_TEXT ${SecCore} $(DESC_SecCore) !insertmacro MUI_DESCRIPTION_TEXT ${SecStartShortcut} $(DESC_SecStartShortcut) !insertmacro MUI_DESCRIPTION_TEXT ${SecDeskShortcut} $(DESC_SecDeskShortcut) !insertmacro MUI_DESCRIPTION_TEXT ${SecQuickShortcut} $(DESC_SecQuickShortcut) !insertmacro MUI_DESCRIPTION_TEXT ${SecLang} $(DESC_SecLang) !insertmacro MUI_FUNCTION_DESCRIPTION_END ;-------------------------------- ; Uninstaller Section !ifdef INNER Section "Uninstall" ; Delete program directory. RMDir /r /REBOOTOK "$INSTDIR" ; Delete start menu shortcuts. RMDir /r "$SMPROGRAMS\InfraRecorder" ; Delete desktop shortcut. Delete "$DESKTOP\InfraRecorder.lnk" ; Delete quick launch shortcut. Delete "$QUICKLAUNCH\InfraRecorder.lnk" DeleteRegKey /ifempty HKCU "Software\InfraRecorder" ; Remove InfraRecorder from Add/Remove Programs. DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\InfraRecorder" SectionEnd !endif ================================================ FILE: src/setup/setup_nsis_vc08.vcproj ================================================ ================================================ FILE: src/setup/setup_nsis_vc10.vcxproj ================================================  Debug Win32 Release Win32 setup_nsis {B8D2451B-06E5-4EBD-8B84-3FA7492A41FF} setup_nsis MakeFileProj Makefile Makefile <_ProjectFileVersion>10.0.30319.1 $(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ makensis.exe $(ProjectDir)setup_nsis.nsi call ..\..\sign.bat ..\..\dist\ir.exe del ..\..\dist\ir.exe makensis.exe $(ProjectDir)setup_nsis.nsi call ..\..\sign.bat ..\..\dist\ir.exe del ..\..\dist\ir.exe setup_nsis.exe WIN32;_DEBUG;$(NMakePreprocessorDefinitions) $(NMakeIncludeSearchPath) $(NMakeForcedIncludes) $(NMakeAssemblySearchPath) $(NMakeForcedUsingAssemblies) $(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ makensis.exe $(ProjectDir)setup_nsis.nsi call ..\..\sign.bat ..\..\dist\ir.exe del ..\..\dist\ir.exe makensis.exe $(ProjectDir)setup_nsis.nsi call ..\..\sign.bat ..\..\dist\ir.exe del ..\..\dist\ir.exe setup_nsis.exe WIN32;NDEBUG;$(NMakePreprocessorDefinitions) $(NMakeIncludeSearchPath) $(NMakeForcedIncludes) $(NMakeAssemblySearchPath) $(NMakeForcedUsingAssemblies) C:\Program Files (x86)\NSIS;$(ExecutablePath) C:\Program Files (x86)\NSIS;$(ExecutablePath) {44e47aba-9695-4a96-bc52-53585c6aaa3c} false {949b73ff-bd75-47c0-b965-328513c481b4} false {533889c9-1598-4823-bfa9-7c97fd35d6df} false {571d4215-38a0-42ce-8ab7-deee9d2154ed} false {da677405-57cd-4e24-ac27-4250a4bf0d1c} false {a6b8e42f-4793-4995-9d63-2906375407ad} false {bc845f0a-9f4d-4a2f-8366-30b816498dbd} false ================================================ FILE: src/setup/setup_nsis_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav Source Files ================================================ FILE: src/setup/setup_wix.bat ================================================ candle setup_wix.wxs -out ..\..\obj\setup_wix\ light -ext WixUIExtension -cultures:en-us ..\..\obj\setup_wix\setup_wix.wixobj -out ..\..\dist\ir_x64.msi ================================================ FILE: src/setup/setup_wix.wxs ================================================ ================================================ FILE: src/setup/setup_wix_vc08.vcproj ================================================ ================================================ FILE: src/setup/setup_wix_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 setup_wix {295627F8-6235-4E9D-992F-F200A7F40173} setup_wix MakeFileProj Makefile Makefile Makefile Makefile <_ProjectFileVersion>10.0.30319.1 $(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ candle setup_wix.wxs -out ..\..\obj\setup_wix\ && light -ext WixUIExtension -cultures:en-us ..\..\obj\setup_wix\setup_wix.wixobj -out ..\..\dist\ir_x64.msi call ..\..\sign.bat ..\..\dist\ir_x64.msi del ..\..\dist\ir.msi del ..\..\dist\ir.wixpdb del ..\..\obj\setup_wix\setup_wix.wixobj candle setup_wix.wxs -out ..\..\obj\setup_wix\ && light -ext WixUIExtension -cultures:en-us ..\..\obj\setup_wix\setup_wix.wixobj -out ..\..\dist\ir_x64.msi call ..\..\sign.bat ..\..\dist\ir_x64.msi del ..\..\dist\ir.msi del ..\..\dist\ir.wixpdb del ..\..\obj\setup_wix\setup_wix.wixobj setup_wix.exe WIN32;_DEBUG;$(NMakePreprocessorDefinitions) $(NMakeIncludeSearchPath) $(NMakeForcedIncludes) $(NMakeAssemblySearchPath) $(NMakeForcedUsingAssemblies) $(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ candle setup_wix.wxs -out ..\..\obj\setup_wix\ && light -ext WixUIExtension -cultures:en-us ..\..\obj\setup_wix\setup_wix.wixobj -out ..\..\dist\ir_x64.msi call ..\..\sign.bat ..\..\dist\ir_x64.msi del ..\..\dist\ir.msi del ..\..\dist\ir.wixpdb del ..\..\obj\setup_wix\setup_wix.wixobj candle setup_wix.wxs -out ..\..\obj\setup_wix\ && light -ext WixUIExtension -cultures:en-us ..\..\obj\setup_wix\setup_wix.wixobj -out ..\..\dist\ir_x64.msi call ..\..\sign.bat ..\..\dist\ir_x64.msi del ..\..\dist\ir.msi del ..\..\dist\ir.wixpdb del ..\..\obj\setup_wix\setup_wix.wixobj setup_wix.exe WIN32;_DEBUG;$(NMakePreprocessorDefinitions) $(NMakeIncludeSearchPath) $(NMakeForcedIncludes) $(NMakeAssemblySearchPath) $(NMakeForcedUsingAssemblies) $(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ candle setup_wix.wxs -out ..\..\obj\setup_wix\ && light -ext WixUIExtension -cultures:en-us ..\..\obj\setup_wix\setup_wix.wixobj -out ..\..\dist\ir_x64.msi call ..\..\sign.bat ..\..\dist\ir_x64.msi del ..\..\dist\ir.msi del ..\..\dist\ir.wixpdb del ..\..\obj\setup_wix\setup_wix.wixobj candle setup_wix.wxs -out ..\..\obj\setup_wix\ && light -ext WixUIExtension -cultures:en-us ..\..\obj\setup_wix\setup_wix.wixobj -out ..\..\dist\ir_x64.msi call ..\..\sign.bat ..\..\dist\ir_x64.msi del ..\..\dist\ir.msi del ..\..\dist\ir.wixpdb del ..\..\obj\setup_wix\setup_wix.wixobj setup_wix.exe WIN32;NDEBUG;$(NMakePreprocessorDefinitions) $(NMakeIncludeSearchPath) $(NMakeForcedIncludes) $(NMakeAssemblySearchPath) $(NMakeForcedUsingAssemblies) $(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ candle setup_wix.wxs -out ..\..\obj\setup_wix\ && light -ext WixUIExtension -cultures:en-us ..\..\obj\setup_wix\setup_wix.wixobj -out ..\..\dist\ir_x64.msi call ..\..\sign.bat ..\..\dist\ir_x64.msi del ..\..\dist\ir.msi del ..\..\dist\ir.wixpdb del ..\..\obj\setup_wix\setup_wix.wixobj candle setup_wix.wxs -out ..\..\obj\setup_wix\ && light -ext WixUIExtension -cultures:en-us ..\..\obj\setup_wix\setup_wix.wixobj -out ..\..\dist\ir_x64.msi call ..\..\sign.bat ..\..\dist\ir_x64.msi del ..\..\dist\ir.msi del ..\..\dist\ir.wixpdb del ..\..\obj\setup_wix\setup_wix.wixobj setup_wix.exe WIN32;NDEBUG;$(NMakePreprocessorDefinitions) $(NMakeIncludeSearchPath) $(NMakeForcedIncludes) $(NMakeAssemblySearchPath) $(NMakeForcedUsingAssemblies) C:\Program Files (x86)\Windows Installer XML v3.5\bin;$(ExecutablePath) C:\Program Files (x86)\Windows Installer XML v3.5\bin;$(ExecutablePath) C:\Program Files (x86)\Windows Installer XML v3.5\bin;$(ExecutablePath) C:\Program Files (x86)\Windows Installer XML v3.5\bin;$(ExecutablePath) {44e47aba-9695-4a96-bc52-53585c6aaa3c} false {949b73ff-bd75-47c0-b965-328513c481b4} false {1a7358f8-3f30-4079-8bab-9399b76b5187} false {da677405-57cd-4e24-ac27-4250a4bf0d1c} false {a6b8e42f-4793-4995-9d63-2906375407ad} false ================================================ FILE: src/setup/setup_wix_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav Source Files ================================================ FILE: src/shell/lang_util.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "lang_util.hh" #include "settings.hh" #include "string_table.hh" TCHAR *lngGetString(unsigned int uiID) { // Try to load translated string. if (g_LanguageSettings.m_pLngProcessor != NULL) { // Make sure that there is a main translation section. if (g_LanguageSettings.m_pLngProcessor->EnterSection(_T("shell"))) { TCHAR *szStrValue; if (g_LanguageSettings.m_pLngProcessor->GetValuePtr(uiID,szStrValue)) return szStrValue; } } // Load internal (English) string. return g_szStringTable[uiID]; } int lngMessageBox(HWND hWnd,unsigned int uiTextID,unsigned int uiCaptionID,unsigned int uiType) { return MessageBox(hWnd,lngGetString(uiTextID),lngGetString(uiCaptionID),uiType); } ================================================ FILE: src/shell/lang_util.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once TCHAR *lngGetString(unsigned int uiID); int lngMessageBox(HWND hWnd,unsigned int uiTextID,unsigned int uiCaptionID,unsigned int uiType); ================================================ FILE: src/shell/readme.txt ================================================ Important note to VC7 and VC8 users: * You may need to change the order of the default include paths in order to compile the project. Make sure that $(VCInstallDir)PlatformSDK\include is above ($VCInstallDir)include in the list. ================================================ FILE: src/shell/resource.h ================================================ //{{NO_DEPENDENCIES}} // Microsoft Visual C++ generated include file. // Used by shell.rc // #define IDS_PROJNAME 100 #define IDR_SHELL 101 #define IDR_SHELLEXT 102 #define IDB_BITMAP1 201 #define IDB_BURNBITMAP 201 // Next default values for new objects // #ifdef APSTUDIO_INVOKED #ifndef APSTUDIO_READONLY_SYMBOLS #define _APS_NEXT_RESOURCE_VALUE 202 #define _APS_NEXT_COMMAND_VALUE 32768 #define _APS_NEXT_CONTROL_VALUE 201 #define _APS_NEXT_SYMED_VALUE 103 #endif #endif ================================================ FILE: src/shell/settings.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include "settings.hh" CLanguageSettings g_LanguageSettings; CGlobalSettings g_GlobalSettings; bool CLanguageSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("Language"))) return false; pXml->GetSafeElementData(_T("LanguageFile"),m_szLanguageFile,MAX_PATH - 1); // Calculate full path. TCHAR szFullPath[MAX_PATH]; ::GetModuleFileName(NULL,szFullPath,MAX_PATH - 1); ExtractFilePath(szFullPath); lstrcat(szFullPath,_T("Languages\\")); lstrcat(szFullPath,m_szLanguageFile); if (ckcore::File::exist(szFullPath)) { m_pLngProcessor = new CLngProcessor(szFullPath); m_pLngProcessor->Load(); } pXml->LeaveElement(); return true; } bool CGlobalSettings::Load(CXmlProcessor *pXml) { if (pXml == NULL) return false; if (!pXml->EnterElement(_T("Global"))) return false; // Shell extension. if (pXml->EnterElement(_T("ShellExtension"))) { pXml->GetSafeElementAttrValue(_T("submenu"),&m_bShellExtSubMenu); pXml->GetSafeElementAttrValue(_T("icons"),&m_bShellExtIcon); pXml->LeaveElement(); } pXml->LeaveElement(); return true; } ================================================ FILE: src/shell/settings.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include class ISettings { public: virtual bool Load(CXmlProcessor *pXml) = 0; }; class CLanguageSettings : public ISettings { public: TCHAR m_szLanguageFile[MAX_PATH]; CLngProcessor *m_pLngProcessor; CLanguageSettings() { m_szLanguageFile[0] = '\0'; m_pLngProcessor = NULL; } ~CLanguageSettings() { if (m_pLngProcessor != NULL) { delete m_pLngProcessor; m_pLngProcessor = NULL; } } bool Load(CXmlProcessor *pXml); }; class CGlobalSettings : public ISettings { public: // Shell extension. bool m_bShellExtSubMenu; bool m_bShellExtIcon; CGlobalSettings() { // Shell extension. m_bShellExtSubMenu = false; m_bShellExtIcon = true; } bool Load(CXmlProcessor *pXml); }; extern CLanguageSettings g_LanguageSettings; extern CGlobalSettings g_GlobalSettings; ================================================ FILE: src/shell/settings_manager.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include #include "settings_manager.hh" #include "string_table.hh" #include "lang_util.hh" CSettingsManager g_SettingsManager; CSettingsManager::CSettingsManager() { RegisterObject(&g_LanguageSettings); RegisterObject(&g_GlobalSettings); } CSettingsManager::~CSettingsManager() { m_Settings.clear(); } void CSettingsManager::RegisterObject(ISettings *pSettings) { m_Settings.push_back(pSettings); } bool CSettingsManager::GetConfigPath(TCHAR *szConfigPath) { #ifdef PORTABLE GetModuleFileName(NULL,szConfigPath,MAX_PATH - 1); ExtractFilePath(szConfigPath); #else if (!SUCCEEDED(SHGetFolderPath(HWND_DESKTOP,CSIDL_APPDATA | CSIDL_FLAG_CREATE,NULL, SHGFP_TYPE_CURRENT,szConfigPath))) return false; IncludeTrailingBackslash(szConfigPath); lstrcat(szConfigPath,_T("InfraRecorder\\")); // Create the file path if it doesn't exist. ckcore::Directory::create(szConfigPath); #endif lstrcat(szConfigPath,_T("settings.xml")); return true; } bool CSettingsManager::Load() { CXmlProcessor Xml; bool bResult = true; // Get the correct file-path. TCHAR szConfigPath[MAX_PATH]; if (!GetConfigPath(szConfigPath)) return false; // Load the file. int iResult = Xml.Load(szConfigPath); if (iResult != XMLRES_OK && iResult != XMLRES_FILEERROR) return false; if (!Xml.EnterElement(_T("InfraRecorder"))) return false; if (!Xml.EnterElement(_T("Settings"))) return false; for (unsigned int i = 0; i < m_Settings.size(); i++) { if (!m_Settings[i]->Load(&Xml)) bResult = false; } Xml.LeaveElement(); Xml.LeaveElement(); return bResult; } ================================================ FILE: src/shell/settings_manager.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include "settings.hh" class CSettingsManager { private: std::vector m_Settings; void RegisterObject(ISettings *pSettings); bool GetConfigPath(TCHAR *szConfigPath); public: CSettingsManager(); ~CSettingsManager(); bool Load(); }; extern CSettingsManager g_SettingsManager; ================================================ FILE: src/shell/shell.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "resource.h" #include "shell.hh" class CShellModule : public CAtlDllModuleT { public : DECLARE_LIBID(LIBID_ShellLib) DECLARE_REGISTRY_APPID_RESOURCEID(IDR_SHELL,"{8E8DAC3C-E7C5-4495-9903-430C1F38CF86}") }; CShellModule _AtlModule; HINSTANCE g_DllInstance = NULL; extern "C" BOOL WINAPI DllMain(HINSTANCE hInstance,DWORD dwReason,LPVOID lpReserved) { g_DllInstance = hInstance; return _AtlModule.DllMain(dwReason,lpReserved); } /* DllCanUnloadNow --------------- Used to determine whether the DLL can be unloaded by OLE. */ STDAPI DllCanUnloadNow() { return _AtlModule.DllCanUnloadNow(); } /* DllGetClassObject ----------------- Returns a class factory to create an object of the requested type. */ STDAPI DllGetClassObject(REFCLSID rclsid,REFIID riid,LPVOID *ppv) { return _AtlModule.DllGetClassObject(rclsid,riid,ppv); } /* DllRegisterServer ----------------- Adds entries to the system registry. */ STDAPI DllRegisterServer() { HRESULT hr = _AtlModule.DllRegisterServer(FALSE); return hr; } /* DllUnregisterServer ------------------- Removes entries from the system registry. */ STDAPI DllUnregisterServer() { HRESULT hr = _AtlModule.DllUnregisterServer(FALSE); return hr; } ================================================ FILE: src/shell/shell.def ================================================ ; shell.def : Declares the module parameters. LIBRARY "shell.DLL" EXPORTS DllCanUnloadNow PRIVATE DllGetClassObject PRIVATE DllRegisterServer PRIVATE DllUnregisterServer PRIVATE ================================================ FILE: src/shell/shell.idl ================================================ // shell.idl : IDL source for shell // // This file will be processed by the MIDL tool to // produce the type library (shell.tlb) and marshalling code. import "oaidl.idl"; import "ocidl.idl"; [ object, uuid(02CEB95B-2C12-40CD-A434-D9F699F4B1AA), helpstring("IShellExt Interface"), pointer_default(unique) ] interface IShellExt : IUnknown{ }; [ uuid(D346209A-7395-4EBF-BFC2-E16294570A1B), version(1.0), helpstring("Shell 1.0 Type Library") ] library ShellLib { importlib("stdole2.tlb"); [ uuid(7022C5BB-445E-4300-99F2-0B7EDA907A53), helpstring("ShellExt Class") ] coclass ShellExt { [default] interface IShellExt; }; }; ================================================ FILE: src/shell/shell.rc ================================================ // Microsoft Visual C++ generated resource script. // #include "resource.h" #define APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 2 resource. // #include "winres.h" ///////////////////////////////////////////////////////////////////////////// #undef APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // Swedish (Sweden) resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_SVE) LANGUAGE LANG_SWEDISH, SUBLANG_SWEDISH #pragma code_page(1252) #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 1 TEXTINCLUDE BEGIN "resource.h\0" END 2 TEXTINCLUDE BEGIN "#include ""winres.h""\r\n" "\0" END 3 TEXTINCLUDE BEGIN "\0" END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Version // VS_VERSION_INFO VERSIONINFO FILEVERSION 0,53,0,0 PRODUCTVERSION 0,53,0,0 FILEFLAGSMASK 0x3fL #ifdef _DEBUG FILEFLAGS 0x1L #else FILEFLAGS 0x0L #endif FILEOS 0x4L FILETYPE 0x2L FILESUBTYPE 0x0L BEGIN BLOCK "StringFileInfo" BEGIN BLOCK "040904b0" BEGIN VALUE "FileDescription", "InfraRecorder Shell Extension" VALUE "FileVersion", "0.53.0.0" VALUE "InternalName", "shell.dll" VALUE "LegalCopyright", "Copyright 2006-2012 Christian Kindahl" VALUE "OriginalFilename", "shell.dll" VALUE "ProductName", "InfraRecorder Shell Extension" VALUE "ProductVersion", "0.53.0.0" END END BLOCK "VarFileInfo" BEGIN VALUE "Translation", 0x409, 1200 END END ///////////////////////////////////////////////////////////////////////////// // // REGISTRY // IDR_SHELL REGISTRY "shell.rgs" IDR_SHELLEXT REGISTRY "shell_ext.rgs" ///////////////////////////////////////////////////////////////////////////// // // Bitmap // IDB_BURNBITMAP BITMAP "Resources\\icon-burn.bmp" ///////////////////////////////////////////////////////////////////////////// // // String Table // STRINGTABLE BEGIN IDS_PROJNAME "shell" END #endif // Swedish (Sweden) resources ///////////////////////////////////////////////////////////////////////////// ================================================ FILE: src/shell/shell.rgs ================================================ HKCR { NoRemove AppID { '%APPID%' = s 'shell' 'shell.DLL' { val AppID = s '%APPID%' } } } ================================================ FILE: src/shell/shell.vcproj.vspscc ================================================ "" { "FILE_VERSION" = "9237" "ENLISTMENT_CHOICE" = "NEVER" "PROJECT_FILE_RELATIVE_PATH" = "" "NUMBER_OF_EXCLUDED_FILES" = "1" "EXCLUDED_FILE0" = "irShell_i.c" "ORIGINAL_PROJECT_FILE_PATH" = "" "NUMBER_OF_NESTED_PROJECTS" = "0" "SOURCE_CONTROL_SETTINGS_PROVIDER" = "PROJECT" } ================================================ FILE: src/shell/shell_ext.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include #include #include "shell_ext.hh" #include "string_table.hh" #include "lang_util.hh" #include "settings_manager.hh" CShellExt::CShellExt() { // Load the configuration. g_SettingsManager.Load(); // Load bitmaps. m_hBurnBitmap = LoadBitmap(g_DllInstance,MAKEINTRESOURCE(IDB_BURNBITMAP)); } CShellExt::~CShellExt() { // Unload bitmaps. if (m_hBurnBitmap != NULL) DeleteObject(m_hBurnBitmap); } HRESULT CShellExt::FinalConstruct() { return S_OK; } void CShellExt::FinalRelease() { } /* CShellExt::IsSeparatorItem ---------------------------- Checks if the specified menu item is a separator and returns true if it is and false otherwise. */ bool CShellExt::IsSeparatorItem(HMENU hMenu,unsigned int uiPosition) { MENUITEMINFO mii; memset(&mii,0,sizeof(MENUITEMINFO)); mii.cbSize = sizeof(MENUITEMINFO); mii.fMask = MIIM_TYPE; ::GetMenuItemInfo(hMenu,uiPosition,TRUE,&mii); return mii.fType == MFT_SEPARATOR; } /* CShellExt::IsProjectFile -------------------------- Determines wheter the specified file is a project file or not. The function returns true if it is a project file, false otherwise. */ bool CShellExt::IsProjectFile(const TCHAR *szFileName) { ckcore::Path FilePath(szFileName); return !lstrcmpi(FilePath.ext_name().c_str(),ckT("irp")); } STDMETHODIMP CShellExt::Initialize(LPCITEMIDLIST pidlFolder, LPDATAOBJECT pDataObj,HKEY hProgID) { FORMATETC fmt = { CF_HDROP,NULL,DVASPECT_CONTENT,-1,TYMED_HGLOBAL }; STGMEDIUM stg = { TYMED_HGLOBAL }; // Check if there is any CF_HDROP data in the data object. if (FAILED(pDataObj->GetData(&fmt,&stg))) return E_INVALIDARG; // Get pointer to data. HDROP hDrop = (HDROP)GlobalLock(stg.hGlobal); if (hDrop == NULL) return E_INVALIDARG; // Get file name. unsigned int uiNumFiles = DragQueryFile(hDrop,0xFFFFFFFF,NULL,NULL); HRESULT hResult = E_INVALIDARG; if (uiNumFiles > 0) { if (DragQueryFile(hDrop,0,m_szFileName,MAX_PATH - 1)) { hResult = S_OK; // Check if we're dealing with a project file. m_bIsProject = IsProjectFile(m_szFileName); } } GlobalUnlock(stg.hGlobal); ReleaseStgMedium(&stg); return hResult; } /* CShellExt::FillProjectMenu ---------------------------- Fills the menu with project related items and retursn the next menu index to be used by any following menu items. */ unsigned int CShellExt::FillProjectMenu(HMENU hMenu,unsigned int uiMenuIndex, unsigned int uiFirstCmd) { // Burn project. InsertMenu(hMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiFirstCmd++,lngGetString(MENU_BURNPROJECT)); if (g_GlobalSettings.m_bShellExtIcon) SetMenuItemBitmaps(hMenu,uiMenuIndex,MF_BYPOSITION,m_hBurnBitmap,NULL); uiMenuIndex++; // Open project. InsertMenu(hMenu,uiMenuIndex++,MF_STRING | MF_BYPOSITION,uiFirstCmd++,lngGetString(MENU_OPENPROJECT)); return uiMenuIndex; } /* CShellExt::FillDiscImageMenu ------------------------------ Fills the menu with disc image related items and returns the next menu index to be used by any following menu items. */ unsigned int CShellExt::FillDiscImageMenu(HMENU hMenu,unsigned int uiMenuIndex, unsigned int uiFirstCmd) { // Burn image. InsertMenu(hMenu,uiMenuIndex,MF_STRING | MF_BYPOSITION,uiFirstCmd++,lngGetString(MENU_BURNIMAGE)); if (g_GlobalSettings.m_bShellExtIcon) SetMenuItemBitmaps(hMenu,uiMenuIndex,MF_BYPOSITION,m_hBurnBitmap,NULL); uiMenuIndex++; return uiMenuIndex; } HRESULT CShellExt::QueryContextMenu(HMENU hmenu,UINT uMenuIndex,UINT uidFirstCmd, UINT uidLastCmd,UINT uFlags) { // Check if we should add any items. if (uFlags & CMF_DEFAULTONLY) return MAKE_HRESULT(SEVERITY_SUCCESS,FACILITY_NULL,0); unsigned int uiFirstMenuIndex = uMenuIndex; // If the item before our item is not a separator we add a new separator. if (!IsSeparatorItem(hmenu,uMenuIndex - 1)) InsertMenu(hmenu,uMenuIndex++,MF_SEPARATOR | MF_BYPOSITION,0,NULL); // Should we add the menu items in a submenu? if (g_GlobalSettings.m_bShellExtSubMenu) { HMENU hPopupMenu = CreatePopupMenu(); if (m_bIsProject) FillProjectMenu(hPopupMenu,0,uidFirstCmd); else FillDiscImageMenu(hPopupMenu,0,uidFirstCmd); InsertMenu(hmenu,uMenuIndex++,MF_BYPOSITION | MF_POPUP,(UINT_PTR)hPopupMenu,_T("InfraRecorder")); } else { if (m_bIsProject) uMenuIndex = FillProjectMenu(hmenu,uMenuIndex,uidFirstCmd); else uMenuIndex = FillDiscImageMenu(hmenu,uMenuIndex,uidFirstCmd); } // If the item below our items is not a separator we add a new separator. if ((unsigned int)GetMenuItemCount(hmenu) > uMenuIndex) { if (!IsSeparatorItem(hmenu,uMenuIndex)) InsertMenu(hmenu,uMenuIndex++,MF_SEPARATOR | MF_BYPOSITION,0,NULL); } return MAKE_HRESULT(SEVERITY_SUCCESS,FACILITY_NULL,uMenuIndex - uiFirstMenuIndex); } HRESULT CShellExt::GetProjectCommandString(LPSTR pszName,UINT cchMax,bool bUnicode, UINT_PTR uiID) { USES_CONVERSION; switch (uiID) { case 0: if (bUnicode) lstrcpynW((LPWSTR)pszName,T2CW(lngGetString(HINT_BURNPROJECT)),cchMax); else lstrcpynA(pszName,T2CA(lngGetString(HINT_BURNPROJECT)),cchMax); return S_OK; case 1: if (bUnicode) lstrcpynW((LPWSTR)pszName,T2CW(lngGetString(HINT_OPENPROJECT)),cchMax); else lstrcpynA(pszName,T2CA(lngGetString(HINT_OPENPROJECT)),cchMax); return S_OK; } return E_INVALIDARG; } HRESULT CShellExt::GetDiscImageCommandString(LPSTR pszName,UINT cchMax,bool bUnicode, UINT_PTR uiID) { USES_CONVERSION; switch (uiID) { case 0: if (bUnicode) lstrcpynW((LPWSTR)pszName,T2CW(lngGetString(HINT_BURNIMAGE)),cchMax); else lstrcpynA(pszName,T2CA(lngGetString(HINT_BURNIMAGE)),cchMax); return S_OK; } return E_INVALIDARG; } HRESULT CShellExt::GetCommandString(UINT_PTR idCmd,UINT uFlags,UINT *pwReserved, LPSTR pszName,UINT cchMax) { // Currently only help strings are supported/supplied. if (uFlags & GCS_HELPTEXT) { if (m_bIsProject) return GetProjectCommandString(pszName,cchMax,(uFlags & GCS_UNICODE) != 0,idCmd); else return GetDiscImageCommandString(pszName,cchMax,(uFlags & GCS_UNICODE) != 0,idCmd); } return E_INVALIDARG; } HRESULT CShellExt::InvokeProjectCommand(HWND hWnd,unsigned int uiID) { TCHAR szParam[MAX_PATH]; TCHAR szFileName[MAX_PATH]; GetModuleFileName(g_DllInstance,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,_T("InfraRecorder.exe")); switch (uiID) { case 0: // Burn project. lstrcpy(szParam,_T("-burnproject ")); lstrcat(szParam,m_szFileName); ShellExecute(HWND_DESKTOP,_T("open"),szFileName,szParam,NULL,SW_SHOWDEFAULT); return S_OK; case 1: // Open project. ShellExecute(HWND_DESKTOP,_T("open"),szFileName,m_szFileName,NULL,SW_SHOWDEFAULT); return S_OK; } return E_INVALIDARG; } HRESULT CShellExt::InvokeDiscImageCommand(HWND hWnd,unsigned int uiID) { TCHAR szParam[MAX_PATH]; TCHAR szFileName[MAX_PATH]; GetModuleFileName(g_DllInstance,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,_T("InfraRecorder.exe")); switch (uiID) { case 0: // Burn image. lstrcpy(szParam,_T("-burnimage ")); lstrcat(szParam,m_szFileName); ShellExecute(HWND_DESKTOP,_T("open"),szFileName,szParam,NULL,SW_SHOWDEFAULT); return S_OK; } return E_INVALIDARG; } HRESULT CShellExt::InvokeCommand(LPCMINVOKECOMMANDINFO pCmdInfo) { // Abort if lpVerb points to a string. if (HIWORD(pCmdInfo->lpVerb) != 0) return E_INVALIDARG; if (m_bIsProject) return InvokeProjectCommand(pCmdInfo->hwnd,LOWORD(pCmdInfo->lpVerb)); else return InvokeDiscImageCommand(pCmdInfo->hwnd,LOWORD(pCmdInfo->lpVerb)); } ================================================ FILE: src/shell/shell_ext.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include #include #include "resource.h" #include "shell.hh" class ATL_NO_VTABLE CShellExt : public CComObjectRootEx, public CComCoClass, public IShellExtInit, public IContextMenu { private: // Is set to true if the selected file is an InfraRecorder project. bool m_bIsProject; // Bitmaps. HBITMAP m_hBurnBitmap; bool IsSeparatorItem(HMENU hMenu,unsigned int uiPosition); bool IsProjectFile(const TCHAR *szFileName); unsigned int FillProjectMenu(HMENU hMenu,unsigned int uiMenuIndex,unsigned int uiFirstCmd); unsigned int FillDiscImageMenu(HMENU hMenu,unsigned int uiMenuIndex,unsigned int uiFirstCmd); HRESULT GetProjectCommandString(LPSTR pszName,UINT cchMax,bool bUnicode,UINT_PTR uiID); HRESULT GetDiscImageCommandString(LPSTR pszName,UINT cchMax,bool bUnicode,UINT_PTR uiID); HRESULT InvokeProjectCommand(HWND hWnd,unsigned int uiID); HRESULT InvokeDiscImageCommand(HWND hWnd,unsigned int uiID); protected: TCHAR m_szFileName[MAX_PATH]; public: CShellExt(); ~CShellExt(); DECLARE_REGISTRY_RESOURCEID(IDR_SHELLEXT) DECLARE_NOT_AGGREGATABLE(CShellExt) BEGIN_COM_MAP(CShellExt) COM_INTERFACE_ENTRY(IShellExtInit) COM_INTERFACE_ENTRY(IContextMenu) END_COM_MAP() DECLARE_PROTECT_FINAL_CONSTRUCT() HRESULT FinalConstruct(); void FinalRelease(); // IShellExtInit. STDMETHODIMP Initialize(LPCITEMIDLIST pidlFolder,LPDATAOBJECT pDataObj,HKEY hProgID); // IContextMenu. STDMETHODIMP QueryContextMenu(HMENU hmenu,UINT uMenuIndex,UINT uidFirstCmd, UINT uidLastCmd,UINT uFlags); STDMETHODIMP GetCommandString(UINT_PTR idCmd,UINT uFlags,UINT *pwReserved, LPSTR pszName,UINT cchMax); STDMETHODIMP InvokeCommand(LPCMINVOKECOMMANDINFO pCmdInfo); }; OBJECT_ENTRY_AUTO(__uuidof(ShellExt),CShellExt) ================================================ FILE: src/shell/shell_ext.rgs ================================================ HKCR { NoRemove CLSID { ForceRemove {7022C5BB-445E-4300-99F2-0B7EDA907A53} = s 'ShellExt Class' { InprocServer32 = s '%MODULE%' { val ThreadingModel = s 'Apartment' } val AppID = s '%APPID%' } } } ================================================ FILE: src/shell/shell_ps.def ================================================ LIBRARY "irShellPS" EXPORTS DllGetClassObject PRIVATE DllCanUnloadNow PRIVATE GetProxyDllInfo PRIVATE DllRegisterServer PRIVATE DllUnregisterServer PRIVATE ================================================ FILE: src/shell/shell_ps_vc08.vcproj ================================================ ================================================ FILE: src/shell/shell_ps_vc08.vcproj.vspscc ================================================ "" { "FILE_VERSION" = "9237" "ENLISTMENT_CHOICE" = "NEVER" "PROJECT_FILE_RELATIVE_PATH" = "" "NUMBER_OF_EXCLUDED_FILES" = "3" "EXCLUDED_FILE0" = "irShell_p.c" "EXCLUDED_FILE1" = "dlldata.c" "EXCLUDED_FILE2" = "irShell_i.c" "ORIGINAL_PROJECT_FILE_PATH" = "" "NUMBER_OF_NESTED_PROJECTS" = "0" "SOURCE_CONTROL_SETTINGS_PROVIDER" = "PROJECT" } ================================================ FILE: src/shell/shell_vc08.vcproj ================================================ ================================================ FILE: src/shell/shell_vc10.vcxproj ================================================  Debug Win32 Debug x64 ReleaseP Win32 ReleaseP x64 Release Win32 Release x64 shell {A6B8E42F-4793-4995-9D63-2906375407AD} shell AtlProj DynamicLibrary Static Unicode DynamicLibrary Static Unicode DynamicLibrary Static Unicode DynamicLibrary Static Unicode DynamicLibrary Static Unicode DynamicLibrary Static Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true true $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true true $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true false $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true false $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true false $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) false false false false false false _DEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)shell.tlb shell.hh shell_i.c shell_p.c Disabled $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;_DEBUG;_USRDLL;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;_ATL_NO_UUIDOF;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 EditAndContinue _DEBUG;%(PreprocessorDefinitions) 0x041d $(IntDir);%(AdditionalIncludeDirectories) ckcored.lib;%(AdditionalDependencies) .\shell.def true Windows $(OutDir)shell.lib MachineX86 Performing registration regsvr32 /s /c "$(TargetPath)" _DEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)shell.tlb shell.hh shell_i.c shell_p.c Disabled $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;_DEBUG;_USRDLL;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;_ATL_NO_UUIDOF;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 ProgramDatabase _DEBUG;%(PreprocessorDefinitions) 0x041d $(IntDir);%(AdditionalIncludeDirectories) ckcored.lib;%(AdditionalDependencies) .\shell.def true Windows $(OutDir)shell.lib MachineX64 Performing registration regsvr32 /s /c "$(TargetPath)" NDEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)shell.tlb shell.hh shell_i.c shell_p.c $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;NDEBUG;_USRDLL;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;_ATL_NO_UUIDOF;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase NDEBUG;%(PreprocessorDefinitions) 0x041d $(IntDir);%(AdditionalIncludeDirectories) ckcore.lib;%(AdditionalDependencies) .\shell.def true Windows true true $(OutDir)shell.lib MachineX86 Performing registration regsvr32 /s /c "$(TargetPath)" NDEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)shell.tlb shell.hh shell_i.c shell_p.c $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;NDEBUG;_USRDLL;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;_ATL_NO_UUIDOF;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase NDEBUG;%(PreprocessorDefinitions) 0x041d $(IntDir);%(AdditionalIncludeDirectories) ckcore.lib;%(AdditionalDependencies) .\shell.def true Windows true true $(OutDir)shell.lib MachineX64 Performing registration regsvr32 /s /c "$(TargetPath)" NDEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)shell.tlb shell.hh shell_i.c shell_p.c $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;NDEBUG;_USRDLL;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;_ATL_NO_UUIDOF;PORTABLE;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase NDEBUG;%(PreprocessorDefinitions) 0x041d $(IntDir);%(AdditionalIncludeDirectories) ckcore.lib;%(AdditionalDependencies) .\shell.def true Windows true true $(OutDir)shell.lib MachineX86 Performing registration regsvr32 /s /c "$(TargetPath)" NDEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)shell.tlb shell.hh shell_i.c shell_p.c $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;NDEBUG;_USRDLL;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;_ATL_NO_UUIDOF;PORTABLE;%(PreprocessorDefinitions) MultiThreaded Use Level3 ProgramDatabase NDEBUG;%(PreprocessorDefinitions) 0x041d $(IntDir);%(AdditionalIncludeDirectories) ckcore.lib;%(AdditionalDependencies) .\shell.def true Windows true true $(OutDir)shell.lib MachineX64 Performing registration regsvr32 /s /c "$(TargetPath)" stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh {81ea1bb3-2ba0-4600-9081-2d2cb9203466} false ================================================ FILE: src/shell/shell_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx {5537b3aa-7890-4cba-a792-675e3fd92e04} False Source Files Source Files Source Files Source Files Source Files Source Files Source Files Generated Files Source Files Header Files Header Files Header Files Header Files Header Files Header Files Header Files Resource Files Resource Files Resource Files Source Files Header Files Resource Files ================================================ FILE: src/shell/stdafx.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" ================================================ FILE: src/shell/stdafx.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #ifndef STRICT #define STRICT #endif // Modify the following defines if you have to target a platform prior to the ones specified below. // Refer to MSDN for the latest info on corresponding values for different platforms. #ifndef WINVER // Allow use of features specific to Windows 95 and Windows NT 4 or later. #define WINVER 0x0400 // Change this to the appropriate value to target Windows 98 and Windows 2000 or later. #endif #define _WIN32_WINNT 0x0500 #ifndef _WIN32_WINDOWS // Allow use of features specific to Windows 98 or later. #define _WIN32_WINDOWS 0x0410 // Change this to the appropriate value to target Windows Me or later. #endif #ifndef _WIN32_IE // Allow use of features specific to IE 4.0 or later. #define _WIN32_IE 0x0500 // Change this to the appropriate value to target IE 5.0 or later. #endif #define _ATL_APARTMENT_THREADED #define _ATL_NO_AUTOMATIC_NAMESPACE #define _ATL_CSTRING_EXPLICIT_CONSTRUCTORS // Some CString constructors will be explicit. // Turns off ATL's hiding of some common and often safely ignored warning messages. #define _ATL_ALL_WARNINGS #include "resource.h" #include #include #include // Global DLL insance supplied by the DLL entrypoint. extern HINSTANCE g_DllInstance; using namespace ATL; ================================================ FILE: src/shell/string_table.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" TCHAR *g_szStringTable[] = { _T("Burn image..."), _T("Burn project..."), _T("Open with InfraRecorder"), _T("Write the disc image contents to a compact disc."), _T("Write the project contents to a compact disc."), _T("Open the project with InfraRecorder.") }; ================================================ FILE: src/shell/string_table.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ enum eStringTable { MENU_BURNIMAGE = 0, MENU_BURNPROJECT, MENU_OPENPROJECT, HINT_BURNIMAGE, HINT_BURNPROJECT, HINT_OPENPROJECT }; extern TCHAR *g_szStringTable[]; ================================================ FILE: src/shell/version.hh ================================================ #define CK_FILEVERSION 0,46,0,0 #define CK_PRODUCTVERSION 0,46,0,0 #define CK_FILEVERSIONSTR "0.46.0.0\0" #define CK_PRODUCTVERSIONSTR "0.46.0.0\0" ================================================ FILE: src/tests/codec.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include #include #include #include #include #include #include #define TEST_CODE(decoder,encoder) \ { \ ckcore::Buffer buffer(num_channels * ((bit_rate / sample_rate) >> 3) * 1024);\ \ __int64 read = 0; \ unsigned __int64 time = 0; \ while (true) \ { \ read = decoder.irc_decode_process(buffer,buffer.size(),time); \ if (read <= 0) \ break; \ \ bool res = encoder.irc_encode_process(buffer,read) >= 0; \ TS_ASSERT(res); \ if (!res) \ break; \ } \ \ TS_ASSERT(encoder.irc_encode_flush() != -1); \ } #define TEST_INIT(decoder,encoder,src_file,dst_file) \ int num_channels = -1,sample_rate = -1,bit_rate = -1; \ unsigned __int64 duration = 0; \ TS_ASSERT(decoder.irc_decode_init(src_file,num_channels,sample_rate,bit_rate,duration));\ TS_ASSERT(encoder.irc_encode_init(dst_file,num_channels,sample_rate,bit_rate)); #define TEST_EXIT(decoder,encoder) \ TS_ASSERT(encoder.irc_encode_exit()); \ TS_ASSERT(decoder.irc_decode_exit()); ckcore::tuint32 get_file_crc(const ckcore::tchar * file_path) { ckcore::FileInStream fis(file_path); if (!fis.open()) { ckcore::tstringstream msg; msg << ckT("could not open \"") << file_path << ckT("\" in order to compute its check-sum."); throw ckcore::Exception2(msg.str()); } ckcore::CrcStream cs(ckcore::CrcStream::ckCRC_32); if (!ckcore::stream::copy(fis,cs)) { ckcore::tstringstream msg; msg << ckT("could not compute check-sum of \"") << file_path << ckT("\"."); throw ckcore::Exception2(msg.str()); } return cs.checksum(); } class CodecTestSuite : public CxxTest::TestSuite { public: void test_mp3_encoder() { #if 1 CCodec sndfile_codec; TS_ASSERT(sndfile_codec.Load(ckT("codecs\\sndfile.irc"))); TS_ASSERT_EQUALS(sndfile_codec.irc_capabilities(),IRC_HAS_DECODER | IRC_HAS_ENCODER); CCodec lame_codec; TS_ASSERT(lame_codec.Load(ckT("codecs\\lame.irc"))); TS_ASSERT_EQUALS(lame_codec.irc_capabilities(),IRC_HAS_ENCODER | IRC_HAS_CONFIG); // Create temporary destination file. ckcore::File tmp = ckcore::File::temp(ckT("ir_test")); // Initialize the Wave decoder. TEST_INIT(sndfile_codec,lame_codec,ckT("..\\..\\..\\src\\tests\\data\\audio\\audio_test_1.wav"),tmp.name().c_str()); TS_ASSERT_EQUALS(num_channels,2); TS_ASSERT_EQUALS(sample_rate,44100); TS_ASSERT_EQUALS(bit_rate,705600); TS_ASSERT_EQUALS(duration,12000); TEST_CODE(sndfile_codec,lame_codec); TEST_EXIT(sndfile_codec,lame_codec); // Compute CRCs. ckcore::tuint32 crc_ref = get_file_crc(ckT("..\\..\\..\\src\\tests\\data\\audio\\audio_test_1-sndfile_lame-standard.mp3")); ckcore::tuint32 crc_tst = get_file_crc(tmp.name().c_str()); // Remove temporary destination file. TS_ASSERT(tmp.remove()); // Compare CRCs. TS_ASSERT_EQUALS(crc_ref,crc_tst); //std::cout << num_channels << std::endl << sample_rate << std::endl << bit_rate << std::endl << duration << std::endl; #endif } void test_wma_encoder() { #if 1 CCodec sndfile_codec; TS_ASSERT(sndfile_codec.Load(ckT("codecs\\sndfile.irc"))); TS_ASSERT_EQUALS(sndfile_codec.irc_capabilities(),IRC_HAS_DECODER | IRC_HAS_ENCODER); CCodec wma_codec; TS_ASSERT(wma_codec.Load(ckT("codecs\\wma.irc"))); TS_ASSERT_EQUALS(wma_codec.irc_capabilities(),IRC_HAS_DECODER | IRC_HAS_ENCODER | IRC_HAS_CONFIG); // Create temporary destination file. ckcore::File tmp = ckcore::File::temp(ckT("ir_test")); // Initialize the Wave decoder. TEST_INIT(sndfile_codec,wma_codec,ckT("..\\..\\..\\src\\tests\\data\\audio\\audio_test_1.wav"),tmp.name().c_str()); TS_ASSERT_EQUALS(num_channels,2); TS_ASSERT_EQUALS(sample_rate,44100); TS_ASSERT_EQUALS(bit_rate,705600); TS_ASSERT_EQUALS(duration,12000); TEST_CODE(sndfile_codec,wma_codec); TEST_EXIT(sndfile_codec,wma_codec); // WMAs seems to inherit some randomness making a CRC comparison // usless, instead compare file sizes for now. ckcore::tint64 size_ref = ckcore::File::size(ckT("..\\..\\..\\src\\tests\\data\\audio\\audio_test_1-sndfile_wma-128.wma")); ckcore::tint64 size_tst = tmp.size(); // Remove temporary destination file. TS_ASSERT(tmp.remove()); // Compare file sizes. TS_ASSERT_EQUALS(size_ref,size_tst); //std::cout << num_channels << std::endl << sample_rate << std::endl << bit_rate << std::endl << duration << std::endl; #endif } void test_ogg_encoder() { #if 1 CCodec sndfile_codec; TS_ASSERT(sndfile_codec.Load(ckT("codecs\\sndfile.irc"))); TS_ASSERT_EQUALS(sndfile_codec.irc_capabilities(),IRC_HAS_DECODER | IRC_HAS_ENCODER); CCodec vorbis_codec; TS_ASSERT(vorbis_codec.Load(ckT("codecs\\vorbis.irc"))); TS_ASSERT_EQUALS(vorbis_codec.irc_capabilities(),IRC_HAS_DECODER | IRC_HAS_ENCODER | IRC_HAS_CONFIG); // Create temporary destination file. ckcore::File tmp = ckcore::File::temp(ckT("ir_test")); // Initialize the Wave decoder. TEST_INIT(sndfile_codec,vorbis_codec,ckT("..\\..\\..\\src\\tests\\data\\audio\\audio_test_1.wav"),tmp.name().c_str()); TS_ASSERT_EQUALS(num_channels,2); TS_ASSERT_EQUALS(sample_rate,44100); TS_ASSERT_EQUALS(bit_rate,705600); TS_ASSERT_EQUALS(duration,12000); TEST_CODE(sndfile_codec,vorbis_codec); TEST_EXIT(sndfile_codec,vorbis_codec); // Ogg Vorbis files seems to inherit some randomness making a CRC // comparison usless, instead compare file sizes for now. ckcore::tint64 size_ref = ckcore::File::size(ckT("..\\..\\..\\src\\tests\\data\\audio\\audio_test_1-sndfile_ogg-quality_mid.ogg")); ckcore::tint64 size_tst = tmp.size(); // Remove temporary destination file. TS_ASSERT(tmp.remove()); // Compare file sizes. TS_ASSERT_EQUALS(size_ref,size_tst); //std::cout << num_channels << std::endl << sample_rate << std::endl << bit_rate << std::endl << duration << std::endl; #endif } }; ================================================ FILE: src/tests/tests_vc08.vcproj ================================================ ================================================ FILE: src/tests/tests_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 tests {2C35640E-0BF9-4BAE-8A0E-3DE5A691D160} tests Win32Proj Application Unicode true Application Unicode Application Unicode true Application Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;C:\Program Files\cxxtest;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;C:\Program Files\cxxtest;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;C:\Program Files\cxxtest;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;C:\Program Files\cxxtest;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) Generating test program. perl -w "c:\program files\cxxtest\cxxtestgen.pl" --error-printer -o test.cc codec.hh Performing Custom Build Step %(Outputs) Disabled $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_CONSOLE;_WINDOWS;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Level3 EditAndContinue ckcored.lib;%(AdditionalDependencies) $(OutDir)$(ProjectName).exe true Console MachineX86 Generating test program. perl -w "c:\program files\cxxtest\cxxtestgen.pl" --error-printer -o test.cc codec.hh Performing Custom Build Step %(Outputs) X64 Disabled $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;_DEBUG;_CONSOLE;_WINDOWS;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Level3 ProgramDatabase ckcored.lib;%(AdditionalDependencies) $(OutDir)$(ProjectName).exe true Console MachineX64 Generating test program. perl -w "c:\program files\cxxtest\cxxtestgen.pl" --error-printer -o test.cc codec.hh $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_CONSOLE;_WINDOWS;_CRT_SECURE_NO_WARNINGS;TEST_SRC_DIR=.;%(PreprocessorDefinitions) MultiThreaded Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) $(OutDir)$(ProjectName).exe true Console true true MachineX86 Generating test program. perl -w "c:\program files\cxxtest\cxxtestgen.pl" --error-printer -o test.cc codec.hh X64 $(ProjectDir)..\;%(AdditionalIncludeDirectories) WIN32;NDEBUG;_CONSOLE;_WINDOWS;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) MultiThreaded Level3 ProgramDatabase ckcore.lib;%(AdditionalDependencies) $(OutDir)$(ProjectName).exe true Console true true MachineX64 {81ea1bb3-2ba0-4600-9081-2d2cb9203466} false ================================================ FILE: src/tests/tests_vc10.vcxproj.filters ================================================  {4FC737F1-C7A5-4376-A066-2A32D752A2FF} cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx {93995380-89BD-4b04-88EB-625FBE52EBFB} h;hpp;hxx;hm;inl;inc;xsd {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav Source Files Header Files ================================================ FILE: src/tools/codectester/codectester.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "resource.h" #include "main_dlg.hh" CAppModule _Module; int Run(LPTSTR lpstrCmdLine = NULL,int nCmdShow = SW_SHOWDEFAULT) { CMessageLoop MainLoop; _Module.AddMessageLoop(&MainLoop); CMainDlg MainDlg; if (MainDlg.Create(NULL) == NULL) { ATLTRACE(_T("Main dialog creation failed!\n")); return 0; } MainDlg.ShowWindow(nCmdShow); int nRet = MainLoop.Run(); _Module.RemoveMessageLoop(); return nRet; } int WINAPI _tWinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance,LPTSTR lpstrCmdLine,int nCmdShow) { HRESULT hRes = ::CoInitialize(NULL); // If you are running on NT 4.0 or higher you can use the following call instead to // make the EXE free threaded. This means that calls come in on a random RPC thread. //HRESULT hRes = ::CoInitializeEx(NULL, COINIT_MULTITHREADED); ATLASSERT(SUCCEEDED(hRes)); // This resolves ATL window thunking problem when Microsoft Layer for Unicode (MSLU) is used. ::DefWindowProc(NULL,0,0,0L); AtlInitCommonControls(ICC_BAR_CLASSES); // Add flags to support other controls. hRes = _Module.Init(NULL,hInstance); ATLASSERT(SUCCEEDED(hRes)); int nRet = Run(lpstrCmdLine,nCmdShow); _Module.Term(); ::CoUninitialize(); return nRet; } ================================================ FILE: src/tools/codectester/codectester.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ ================================================ FILE: src/tools/codectester/codectester.rc ================================================ // Microsoft Visual C++ generated resource script. // #include "Resource.h" #define APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 2 resource. // #include "atlres.h" ///////////////////////////////////////////////////////////////////////////// #undef APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // English (U.S.) resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) #ifdef _WIN32 LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US #pragma code_page(1252) #endif //_WIN32 #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 1 TEXTINCLUDE BEGIN "Resource.h\0" END 2 TEXTINCLUDE BEGIN "#include ""atlres.h""\r\n" "\0" END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Icon // // Icon with lowest ID value placed first to ensure application icon // remains consistent on all systems. IDR_MAINFRAME ICON "resources\\icon-main.ico" ///////////////////////////////////////////////////////////////////////////// // // Dialog // IDD_MAINDLG DIALOGEX 0, 0, 328, 190 STYLE DS_SETFONT | WS_MINIMIZEBOX | WS_CAPTION | WS_SYSMENU CAPTION "Codec Tester" FONT 8, "MS Sans Serif", 0, 0, 0x0 BEGIN DEFPUSHBUTTON "Start",IDOK,271,18,50,14 PUSHBUTTON "Exit",IDCANCEL,271,35,50,14 PUSHBUTTON "About...",ID_APP_ABOUT,271,169,50,14 LTEXT "Installed codecs (double-click to view copyright note):",IDC_INSTALLEDSTATIC,7,7,170,8 CONTROL "",IDC_LIST,"SysListView32",LVS_REPORT | LVS_SINGLESEL | LVS_ALIGNLEFT | WS_BORDER | WS_TABSTOP,7,18,257,102 GROUPBOX "Parameters",IDC_OPTIONSSTATIC,7,123,257,59 CONTROL "",IDC_PROGRESS,"msctls_progress32",NOT WS_VISIBLE | WS_BORDER,7,124,258,10 LTEXT "Source file:",IDC_INPUTSTATIC,12,134,36,8 EDITTEXT IDC_INPUTEDIT,61,132,177,13,ES_AUTOHSCROLL PUSHBUTTON "...",IDC_INPUTBUTTON,243,132,15,13 LTEXT "Target folder:",IDC_OUTPUTSTATIC,12,150,43,8 EDITTEXT IDC_OUTPUTEDIT,61,148,177,13,ES_AUTOHSCROLL LTEXT "Target format:",IDC_FORMATSTATIC,12,166,45,8 COMBOBOX IDC_FORMATCOMBO,62,164,98,49,CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP PUSHBUTTON "...",IDC_OUTPUTBUTTON,243,148,15,13 PUSHBUTTON "Help...",IDC_HELPBUTTON,271,152,50,14 PUSHBUTTON "Configure...",IDC_ENCODERCONFIGBUTTON,164,164,43,13 END ///////////////////////////////////////////////////////////////////////////// // // DESIGNINFO // #ifdef APSTUDIO_INVOKED GUIDELINES DESIGNINFO BEGIN IDD_MAINDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 321 TOPMARGIN, 7 BOTTOMMARGIN, 183 END END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Accelerator // IDR_MAINFRAME ACCELERATORS BEGIN "N", ID_FILE_NEW, VIRTKEY, CONTROL "O", ID_FILE_OPEN, VIRTKEY, CONTROL "S", ID_FILE_SAVE, VIRTKEY, CONTROL "P", ID_FILE_PRINT, VIRTKEY, CONTROL "Z", ID_EDIT_UNDO, VIRTKEY, CONTROL "X", ID_EDIT_CUT, VIRTKEY, CONTROL "C", ID_EDIT_COPY, VIRTKEY, CONTROL "V", ID_EDIT_PASTE, VIRTKEY, CONTROL VK_BACK, ID_EDIT_UNDO, VIRTKEY, ALT VK_DELETE, ID_EDIT_CUT, VIRTKEY, SHIFT VK_INSERT, ID_EDIT_COPY, VIRTKEY, CONTROL VK_INSERT, ID_EDIT_PASTE, VIRTKEY, SHIFT VK_F6, ID_NEXT_PANE, VIRTKEY VK_F6, ID_PREV_PANE, VIRTKEY, SHIFT END ///////////////////////////////////////////////////////////////////////////// // // Version // VS_VERSION_INFO VERSIONINFO FILEVERSION 0,4,0,3 PRODUCTVERSION 0,4,0,3 FILEFLAGSMASK 0x3fL #ifdef _DEBUG FILEFLAGS 0x1L #else FILEFLAGS 0x0L #endif FILEOS 0x4L FILETYPE 0x2L FILESUBTYPE 0x0L BEGIN BLOCK "StringFileInfo" BEGIN BLOCK "040904b0" BEGIN VALUE "FileDescription", "InfraRecorder Codec Tester" VALUE "FileVersion", "0.4.0.3" VALUE "InternalName", "codectester" VALUE "LegalCopyright", "Copyright 2006-2010 Christian Kindahl" VALUE "OriginalFilename", "codectester.exe" VALUE "ProductName", "InfraRecorder Codec Tester" VALUE "ProductVersion", "0.4.0.3" END END BLOCK "VarFileInfo" BEGIN VALUE "Translation", 0x409, 1200 END END ///////////////////////////////////////////////////////////////////////////// // // String Table // STRINGTABLE BEGIN IDR_MAINFRAME "CodecTester" END STRINGTABLE BEGIN ID_FILE_NEW "Create a new document\nNew" ID_FILE_OPEN "Open an existing document\nOpen" ID_FILE_CLOSE "Close the active document\nClose" ID_FILE_SAVE "Save the active document\nSave" ID_FILE_SAVE_AS "Save the active document with a new name\nSave As" ID_FILE_PAGE_SETUP "Change the printing options\nPage Setup" ID_FILE_PRINT_SETUP "Change the printer and printing options\nPrint Setup" ID_FILE_PRINT "Print the active document\nPrint" ID_FILE_PRINT_PREVIEW "Display full pages\nPrint Preview" END STRINGTABLE BEGIN ID_APP_ABOUT "Display program information, version number and copyright\nAbout" ID_APP_EXIT "Quit the application; prompts to save documents\nExit" END STRINGTABLE BEGIN ID_NEXT_PANE "Switch to the next window pane\nNext Pane" ID_PREV_PANE "Switch back to the previous window pane\nPrevious Pane" END STRINGTABLE BEGIN ID_WINDOW_NEW "Open another window for the active document\nNew Window" ID_WINDOW_ARRANGE "Arrange icons at the bottom of the window\nArrange Icons" ID_WINDOW_CASCADE "Arrange windows so they overlap\nCascade Windows" ID_WINDOW_TILE_HORZ "Arrange windows as non-overlapping tiles\nTile Windows" ID_WINDOW_TILE_VERT "Arrange windows as non-overlapping tiles\nTile Windows" ID_WINDOW_SPLIT "Split the active window into panes\nSplit" END STRINGTABLE BEGIN ID_EDIT_CLEAR "Erase the selection\nErase" ID_EDIT_CLEAR_ALL "Erase everything\nErase All" ID_EDIT_COPY "Copy the selection and put it on the Clipboard\nCopy" ID_EDIT_CUT "Cut the selection and put it on the Clipboard\nCut" ID_EDIT_FIND "Find the specified text\nFind" ID_EDIT_PASTE "Insert Clipboard contents\nPaste" ID_EDIT_REPEAT "Repeat the last action\nRepeat" ID_EDIT_REPLACE "Replace specific text with different text\nReplace" ID_EDIT_SELECT_ALL "Select the entire document\nSelect All" ID_EDIT_UNDO "Undo the last action\nUndo" ID_EDIT_REDO "Redo the previously undone action\nRedo" END STRINGTABLE BEGIN ATL_IDS_SCSIZE "Change the window size" ATL_IDS_SCMOVE "Change the window position" ATL_IDS_SCMINIMIZE "Reduce the window to an icon" ATL_IDS_SCMAXIMIZE "Enlarge the window to full size" ATL_IDS_SCNEXTWINDOW "Switch to the next document window" ATL_IDS_SCPREVWINDOW "Switch to the previous document window" ATL_IDS_SCCLOSE "Close the active window and prompts to save the documents" END STRINGTABLE BEGIN ATL_IDS_SCRESTORE "Restore the window to normal size" ATL_IDS_SCTASKLIST "Activate Task List" ATL_IDS_MDICHILD "Activate this window" END STRINGTABLE BEGIN ATL_IDS_IDLEMESSAGE "Ready" END STRINGTABLE BEGIN ATL_IDS_MRU_FILE "Open this document" END #endif // English (U.S.) resources ///////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////// // Swedish resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_SVE) #ifdef _WIN32 LANGUAGE LANG_SWEDISH, SUBLANG_DEFAULT #pragma code_page(1252) #endif //_WIN32 #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 3 TEXTINCLUDE BEGIN "\r\0" END #endif // APSTUDIO_INVOKED #endif // Swedish resources ///////////////////////////////////////////////////////////////////////////// #ifndef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 3 resource. // ///////////////////////////////////////////////////////////////////////////// #endif // not APSTUDIO_INVOKED ================================================ FILE: src/tools/codectester/codectester_vc08.vcproj ================================================ ================================================ FILE: src/tools/codectester/codectester_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 Template Win32 Template x64 codectester {662C79E3-70D3-4F83-BAAF-EC663B93BAFD} codectester Application Unicode Application Unicode Application Application Unicode Application Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) _DEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)codectester.tlb codectester.hh codectester_i.c codectester_p.c Disabled $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;_DEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 EditAndContinue _DEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) ckcored.lib;%(AdditionalDependencies) true Windows MachineX86 _DEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)codectester.tlb codectester.hh codectester_i.c codectester_p.c Disabled $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;_DEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 ProgramDatabase _DEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) ckcored.lib;%(AdditionalDependencies) true Windows MachineX64 NDEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)codectester.tlb codectester.hh codectester_i.c codectester_p.c $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;NDEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) Sync MultiThreaded Use Level3 NDEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) /NODEFAULTLIB:atlmincrt.lib %(AdditionalOptions) ckcore.lib;%(AdditionalDependencies) Windows MachineX86 NDEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)codectester.tlb codectester.hh codectester_i.c codectester_p.c $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;NDEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) Sync MultiThreaded Use Level3 NDEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) /NODEFAULTLIB:atlmincrt.lib %(AdditionalOptions) ckcore.lib;%(AdditionalDependencies) Windows MachineX64 stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh {81ea1bb3-2ba0-4600-9081-2d2cb9203466} false ================================================ FILE: src/tools/codectester/codectester_vc10.vcxproj.filters ================================================  {ce6fd350-77e2-441a-9fd4-dfe011fb9a7c} cpp;c;cxx;def;odl;idl;hpj;bat;asm {8dc5110c-0bcf-47ae-b5e9-0c2b79cdb582} h;hpp;hxx;hm;inl;inc {edbcdaee-2964-4ab4-b83b-8fed990499f0} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;jpg;jpeg;jpe;manifest Source Files Source Files Source Files Header Files Header Files Header Files Resource Files Header Files Resource Files ================================================ FILE: src/tools/codectester/main_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "resource.h" #include #include #include "main_dlg.hh" CCodecManager g_CodecManager; BOOL CMainDlg::PreTranslateMessage(MSG *pMsg) { return CWindow::IsDialogMessage(pMsg); } BOOL CMainDlg::OnIdle() { return FALSE; } void CALLBACK CodecMessage(int iType,const TCHAR *szMessage) { switch (iType) { case IRC_MESSAGE_WARNING: MessageBox(HWND_DESKTOP,szMessage,_T("Warning"),MB_OK | MB_ICONWARNING); break; case IRC_MESSAGE_ERROR: MessageBox(HWND_DESKTOP,szMessage,_T("Error"),MB_OK | MB_ICONERROR); break; default: MessageBox(HWND_DESKTOP,szMessage,_T("Information"),MB_OK | MB_ICONINFORMATION); break; } } void CMainDlg::InitializeListView() { // Create the image list. m_hListImageList = NULL; HINSTANCE hInstance = LoadLibrary(_T("shell32.dll")); HICON hIcon = (HICON)LoadImage(hInstance,MAKEINTRESOURCE(278),IMAGE_ICON,16,16,LR_LOADTRANSPARENT); FreeLibrary(hInstance); m_hListImageList = ImageList_Create(16,16,ILC_COLOR32,0,1); ImageList_AddIcon(m_hListImageList,hIcon); DestroyIcon(hIcon); // Setup the list view. m_ListView.SetImageList(m_hListImageList,LVSIL_NORMAL); m_ListView.SetImageList(m_hListImageList,LVSIL_SMALL); m_ListView.SetExtendedListViewStyle(LVS_EX_FULLROWSELECT); // Add the columns. m_ListView.AddColumn(_T("Name"),0); m_ListView.SetColumnWidth(0,150); m_ListView.AddColumn(_T("Version"),1,-1,LVCF_FMT | LVCF_WIDTH | LVCF_TEXT | LVCF_SUBITEM,LVCFMT_RIGHT); m_ListView.SetColumnWidth(1,55); } void CMainDlg::FillListView() { TCHAR szFileName[MAX_PATH]; int iItemCount = 0; for (unsigned int i = 0; i < g_CodecManager.m_Codecs.size(); i++) { if (g_CodecManager.m_Codecs[i]->GetFileName(szFileName,MAX_PATH - 1)) { ExtractFileName(szFileName); m_ListView.AddItem(iItemCount,0,szFileName,0); m_ListView.AddItem(iItemCount,1,g_CodecManager.m_Codecs[i]->irc_string(IRC_STR_VERSION),0); iItemCount++; } } } void CMainDlg::FillComboBox() { m_ComboBox.ResetContent(); for (unsigned int i = 0; i < g_CodecManager.m_Codecs.size(); i++) { if (g_CodecManager.m_Codecs[i]->irc_capabilities() & IRC_HAS_ENCODER) { m_ComboBox.AddString(g_CodecManager.m_Codecs[i]->irc_string(IRC_STR_ENCODER)); m_ComboBox.SetItemData(m_ComboBox.GetCount() - 1,(DWORD_PTR)g_CodecManager.m_Codecs[i]); } } if (m_ComboBox.GetCount() == 0) { DisableApp(); return; } m_ComboBox.SetCurSel(0); CCodec *pEncoder = (CCodec *)m_ComboBox.GetItemData(0); ::EnableWindow(GetDlgItem(IDC_ENCODERCONFIGBUTTON),pEncoder->irc_capabilities() & IRC_HAS_CONFIG); } void CMainDlg::DisableApp() { m_ComboBox.AddString(_T("None")); m_ComboBox.EnableWindow(FALSE); ::EnableWindow(GetDlgItem(IDOK),FALSE); m_ComboBox.SetCurSel(0); } LRESULT CMainDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the dialog on the screen. CenterWindow(); m_ListView = GetDlgItem(IDC_LIST); m_ComboBox = GetDlgItem(IDC_FORMATCOMBO); // Set icons. HICON hIcon = (HICON)::LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDR_MAINFRAME), IMAGE_ICON,::GetSystemMetrics(SM_CXICON),::GetSystemMetrics(SM_CYICON),LR_DEFAULTCOLOR); SetIcon(hIcon, TRUE); HICON hIconSmall = (HICON)::LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDR_MAINFRAME), IMAGE_ICON,::GetSystemMetrics(SM_CXSMICON),::GetSystemMetrics(SM_CYSMICON),LR_DEFAULTCOLOR); SetIcon(hIconSmall,FALSE); // Register object for message filtering and idle updates. CMessageLoop *pLoop = _Module.GetMessageLoop(); ATLASSERT(pLoop != NULL); pLoop->AddMessageFilter(this); pLoop->AddIdleHandler(this); UIAddChildWindowContainer(m_hWnd); // Initialize the list view. InitializeListView(); // Setup controls. ::SendMessage(GetDlgItem(IDC_INPUTEDIT),EM_SETLIMITTEXT,MAX_PATH - 1,0); ::SendMessage(GetDlgItem(IDC_OUTPUTEDIT),EM_SETLIMITTEXT,MAX_PATH - 1,0); // Temp... //SetDlgItemText(IDC_INPUTEDIT,_T("C:\\Temp\\AudioFiles\\Test2.wav")); //SetDlgItemText(IDC_OUTPUTEDIT,_T("C:\\Temp\\AudioOut\\")); // Temp... // Load the codecs. TCHAR szCodecPath[MAX_PATH]; GetModuleFileName(NULL,szCodecPath,MAX_PATH - 1); ExtractFilePath(szCodecPath); lstrcat(szCodecPath,_T("codecs\\")); if (g_CodecManager.LoadCodecs(szCodecPath)) { // Fill the codec list view. FillListView(); // Fill the target format combo box. FillComboBox(); } else { MessageBox(_T("Unable to load codecs."),_T("Error"),MB_OK | MB_ICONERROR); DisableApp(); } return TRUE; } LRESULT CMainDlg::OnAppAbout(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { MessageBox(_T("Copyright 2006-2012 Christian Kindahl"),_T("About"),MB_OK | MB_ICONINFORMATION); return 0; } void CMainDlg::BeginProcess() { ::ShowWindow(GetDlgItem(IDC_INPUTSTATIC),SW_HIDE); ::ShowWindow(GetDlgItem(IDC_INPUTEDIT),SW_HIDE); ::ShowWindow(GetDlgItem(IDC_INPUTBUTTON),SW_HIDE); ::ShowWindow(GetDlgItem(IDC_OUTPUTSTATIC),SW_HIDE); ::ShowWindow(GetDlgItem(IDC_OUTPUTEDIT),SW_HIDE); ::ShowWindow(GetDlgItem(IDC_OUTPUTBUTTON),SW_HIDE); ::ShowWindow(GetDlgItem(IDC_FORMATSTATIC),SW_HIDE); ::ShowWindow(GetDlgItem(IDC_FORMATCOMBO),SW_HIDE); ::ShowWindow(GetDlgItem(IDC_OPTIONSSTATIC),SW_HIDE); ::ShowWindow(GetDlgItem(IDC_PROGRESS),SW_SHOW); SendDlgItemMessage(IDC_PROGRESS,PBM_SETRANGE32,0,100); } void CMainDlg::EndProcess() { ::ShowWindow(GetDlgItem(IDC_INPUTSTATIC),SW_SHOW); ::ShowWindow(GetDlgItem(IDC_INPUTEDIT),SW_SHOW); ::ShowWindow(GetDlgItem(IDC_INPUTBUTTON),SW_SHOW); ::ShowWindow(GetDlgItem(IDC_OUTPUTSTATIC),SW_SHOW); ::ShowWindow(GetDlgItem(IDC_OUTPUTEDIT),SW_SHOW); ::ShowWindow(GetDlgItem(IDC_OUTPUTBUTTON),SW_SHOW); ::ShowWindow(GetDlgItem(IDC_FORMATSTATIC),SW_SHOW); ::ShowWindow(GetDlgItem(IDC_FORMATCOMBO),SW_SHOW); ::ShowWindow(GetDlgItem(IDC_OPTIONSSTATIC),SW_SHOW); ::ShowWindow(GetDlgItem(IDC_PROGRESS),SW_HIDE); } LRESULT CMainDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { TCHAR szSourceFile[MAX_PATH]; GetDlgItemText(IDC_INPUTEDIT,szSourceFile,MAX_PATH - 1); // Display the progress bar. BeginProcess(); // Find which codec that can be uses for decoding the source file. CCodec *pDecoder = NULL; // Source file information. int iNumChannels = -1; int iSampleRate = -1; int iBitRate = -1; unsigned __int64 uiDuration = 0; for (unsigned int i = 0; i < g_CodecManager.m_Codecs.size(); i++) { // We're only interested in decoders. if ((g_CodecManager.m_Codecs[i]->irc_capabilities() & IRC_HAS_DECODER) == 0) continue; if (g_CodecManager.m_Codecs[i]->irc_decode_init(szSourceFile,iNumChannels, iSampleRate,iBitRate,uiDuration)) { pDecoder = g_CodecManager.m_Codecs[i]; break; } } if (pDecoder == NULL) { MessageBox(_T("There is no installed codec that support the specified source file."),_T("Error"),MB_OK | MB_ICONERROR); EndProcess(); return 0; } // Encoder. CCodec *pEncoder = (CCodec *)m_ComboBox.GetItemData(m_ComboBox.GetCurSel()); // Setup target path. TCHAR szTargetFile[MAX_PATH],szTargetFileName[MAX_PATH]; lstrcpy(szTargetFileName,szSourceFile); ExtractFileName(szTargetFileName); ChangeFileExt(szTargetFileName,pEncoder->irc_string(IRC_STR_FILEEXT)); GetDlgItemText(IDC_OUTPUTEDIT,szTargetFile,MAX_PATH - 1); IncludeTrailingBackslash(szTargetFile); lstrcat(szTargetFile,szTargetFileName); // Initialize the encoder. if (!pEncoder->irc_encode_init(szTargetFile,iNumChannels,iSampleRate,iBitRate)) { MessageBox(_T("Failed to initialize the encoder."),_T("Error"),MB_OK | MB_ICONERROR); EndProcess(); return 0; } // Setup callbacks. pDecoder->irc_set_callback(CodecMessage); pEncoder->irc_set_callback(CodecMessage); // Encode/decode-process. __int64 iBytesRead = 0; unsigned __int64 uiCurrentTime = 0; // Allocate buffer memory. unsigned int uiBufferSize = iNumChannels * ((iBitRate / iSampleRate) >> 3) * ENCODE_BUFFER_FACTOR; unsigned char *pBuffer = new unsigned char[uiBufferSize]; while (true) { iBytesRead = pDecoder->irc_decode_process(pBuffer,uiBufferSize,uiCurrentTime); if (iBytesRead <= 0) break; if (pEncoder->irc_encode_process(pBuffer,iBytesRead) < 0) { MessageBox(_T("Failed to encode data."),_T("Error"),MB_OK | MB_ICONERROR); break; } // Update the progres bar. int iPercent = (int)(((double)uiCurrentTime/uiDuration) * 100); SendDlgItemMessage(IDC_PROGRESS,PBM_SETPOS,(WPARAM)iPercent,0); TCHAR szTemp[25]; swprintf(szTemp,_T("%d"),iPercent); SetWindowText(szTemp); } // Free buffer memory. delete [] pBuffer; // Flush. pEncoder->irc_encode_flush(); // Destroy the codecs. pEncoder->irc_encode_exit(); pDecoder->irc_decode_exit(); // Hide the progress bar. EndProcess(); return 0; } LRESULT CMainDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CloseDialog(wID); return 0; } void CMainDlg::CloseDialog(int iVal) { DestroyWindow(); ::PostQuitMessage(iVal); // Destroy the image list. if (m_hListImageList) ImageList_Destroy(m_hListImageList); } LRESULT CMainDlg::OnBnClickedInputbutton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { WTL::CFileDialog FileDialog(true,0,0,OFN_FILEMUSTEXIST | OFN_EXPLORER, _T("All Files (*.*)\0*.*\0\0"),m_hWnd); if (FileDialog.DoModal() == IDOK) SetDlgItemText(IDC_INPUTEDIT,FileDialog.m_szFileName); return 0; } LRESULT CMainDlg::OnBnClickedOutputbutton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CFolderDialog FolderDialog(m_hWnd,_T("Please select a target folder:"),BIF_NEWDIALOGSTYLE | BIF_RETURNONLYFSDIRS); if (FolderDialog.DoModal() == IDOK) SetDlgItemText(IDC_OUTPUTEDIT,FolderDialog.GetFolderPath()); return 0; } LRESULT CMainDlg::OnBnClickedHelpbutton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { MessageBox(_T("A decoder will automatically be choosen to match the selected source file. If no such decoder can be found the process will be aborted."),_T("Help"),MB_OK | MB_ICONINFORMATION); return 0; } LRESULT CMainDlg::OnBnClickedEncoderConfigButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CCodec *pEncoder = (CCodec *)m_ComboBox.GetItemData(m_ComboBox.GetCurSel()); pEncoder->irc_encode_config(); return 0; } LRESULT CMainDlg::OnEncoderChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CCodec *pEncoder = (CCodec *)m_ComboBox.GetItemData(m_ComboBox.GetCurSel()); ::EnableWindow(GetDlgItem(IDC_ENCODERCONFIGBUTTON),pEncoder->irc_capabilities() & IRC_HAS_CONFIG); return 0; } LRESULT CMainDlg::OnListDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled) { if (m_ListView.GetSelectedCount() > 0) { unsigned int uiCodec = m_ListView.GetSelectedIndex(); MessageBox(g_CodecManager.m_Codecs[uiCodec]->irc_string(IRC_STR_ABOUT),_T("Information"),MB_OK | MB_ICONINFORMATION); } bHandled = false; return 0; } ================================================ FILE: src/tools/codectester/main_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #define ENCODE_BUFFER_FACTOR 1024 #pragma once class CMainDlg : public CDialogImpl,public CUpdateUI, public CMessageFilter,public CIdleHandler { private: HIMAGELIST m_hListImageList; CListViewCtrl m_ListView; CComboBox m_ComboBox; void InitializeListView(); void FillListView(); void FillComboBox(); void DisableApp(); void BeginProcess(); void EndProcess(); public: enum { IDD = IDD_MAINDLG }; virtual BOOL PreTranslateMessage(MSG *pMsg); virtual BOOL OnIdle(); BEGIN_UPDATE_UI_MAP(CMainDlg) END_UPDATE_UI_MAP() BEGIN_MSG_MAP(CMainDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) COMMAND_ID_HANDLER(ID_APP_ABOUT,OnAppAbout) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) COMMAND_HANDLER(IDC_INPUTBUTTON,BN_CLICKED,OnBnClickedInputbutton) COMMAND_HANDLER(IDC_OUTPUTBUTTON,BN_CLICKED,OnBnClickedOutputbutton) COMMAND_HANDLER(IDC_HELPBUTTON,BN_CLICKED,OnBnClickedHelpbutton) COMMAND_HANDLER(IDC_ENCODERCONFIGBUTTON,BN_CLICKED,OnBnClickedEncoderConfigButton) COMMAND_HANDLER(IDC_FORMATCOMBO,CBN_SELCHANGE,OnEncoderChange) NOTIFY_HANDLER(IDC_LIST,NM_DBLCLK,OnListDblClick) END_MSG_MAP() void CloseDialog(int iVal); LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnAppAbout(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnBnClickedInputbutton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnBnClickedOutputbutton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnBnClickedHelpbutton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnBnClickedEncoderConfigButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnEncoderChange(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnListDblClick(int iCtrlID,LPNMHDR pNMH,BOOL &bHandled); }; ================================================ FILE: src/tools/codectester/resource.h ================================================ //{{NO_DEPENDENCIES}} // Microsoft Visual C++ generated include file. // Used by CodecTester.rc // #define IDR_MAINFRAME 128 #define IDD_MAINDLG 129 #define IDC_INSTALLEDSTATIC 1000 #define IDC_LIST 1001 #define IDC_INPUTSTATIC 1002 #define IDC_INPUTEDIT 1003 #define IDC_OUTPUTSTATIC 1004 #define IDC_OUTPUTEDIT 1005 #define IDC_FORMATSTATIC 1006 #define IDC_FORMATCOMBO 1007 #define IDC_INPUTBUTTON 1008 #define IDC_INPUTBUTTON2 1009 #define IDC_OUTPUTBUTTON 1009 #define IDC_PROGRESS 1010 #define IDC_OPTIONSSTATIC 1011 #define IDC_HELPBUTTON 1012 #define IDC_BUTTON1 1013 #define IDC_ENCODERCONFIGBUTTON 1013 // Next default values for new objects // #ifdef APSTUDIO_INVOKED #ifndef APSTUDIO_READONLY_SYMBOLS #define _APS_NEXT_RESOURCE_VALUE 201 #define _APS_NEXT_COMMAND_VALUE 32772 #define _APS_NEXT_CONTROL_VALUE 1014 #define _APS_NEXT_SYMED_VALUE 101 #endif #endif ================================================ FILE: src/tools/codectester/stdafx.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #if (_ATL_VER < 0x0700) #include #endif //(_ATL_VER < 0x0700) ================================================ FILE: src/tools/codectester/stdafx.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once // Change these values to use different versions. #define WINVER 0x0400 //#define _WIN32_WINNT 0x0400 #define _WIN32_IE 0x0400 #define _RICHEDIT_VER 0x0100 #include #include extern CAppModule _Module; #include #include #include #include // Manifest. #if defined _M_IX86 #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='x86' publicKeyToken='6595b64144ccf1df' language='*'\"") #elif defined _M_IA64 #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='ia64' publicKeyToken='6595b64144ccf1df' language='*'\"") #elif defined _M_X64 #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='amd64' publicKeyToken='6595b64144ccf1df' language='*'\"") #else #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='*' publicKeyToken='6595b64144ccf1df' language='*'\"") #endif ================================================ FILE: src/tools/translationtool/lng_analyzer.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "lng_analyzer.hh" CLngAnalyzer::CLngAnalyzer(const TCHAR *szFullPath) : CLngProcessor(szFullPath) { } CLngAnalyzer::~CLngAnalyzer() { } unsigned int CLngAnalyzer::GetNumValues() { unsigned int uiResult = 0; for (unsigned int i = 0; i < m_pSections.size(); i++) uiResult += (unsigned int)m_pSections[i]->m_Values.size(); return uiResult; } unsigned int CLngAnalyzer::GetNumSections() { return (unsigned int)m_pSections.size(); } CLngSection *CLngAnalyzer::GetSection(unsigned int uiIndex) { if (uiIndex > m_pSections.size()) return NULL; return m_pSections[uiIndex]; } CLngSection *CLngAnalyzer::GetSection(const TCHAR *szName) { for (unsigned int i = 0; i < m_pSections.size(); i++) { if (!lstrcmp(m_pSections[i]->m_szName,szName)) return m_pSections[i]; } return NULL; } bool CLngAnalyzer::SectionHasValue(CLngSection *pSection,unsigned long ulName) { for (unsigned int i = 0; i < pSection->m_Values.size(); i++) { if (pSection->m_Values[i]->ulName == ulName) return true; } return false; } ================================================ FILE: src/tools/translationtool/lng_analyzer.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include class CLngAnalyzer : public CLngProcessor { public: CLngAnalyzer(const TCHAR *szFullPath); ~CLngAnalyzer(); unsigned int GetNumValues(); unsigned int GetNumSections(); CLngSection *GetSection(unsigned int uiIndex); CLngSection *GetSection(const TCHAR *szName); bool SectionHasValue(CLngSection *pSection,unsigned long ulName); }; ================================================ FILE: src/tools/translationtool/main_dlg.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "resource.h" #include "lng_analyzer.hh" #include "main_dlg.hh" BOOL CMainDlg::PreTranslateMessage(MSG *pMsg) { return CWindow::IsDialogMessage(pMsg); } BOOL CMainDlg::OnIdle() { return FALSE; } void CMainDlg::CloseDialog(int iVal) { DestroyWindow(); ::PostQuitMessage(iVal); } LRESULT CMainDlg::OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { // Center the dialog on the screen. CenterWindow(); DlgResize_Init(true,true,WS_CLIPCHILDREN); // Set icons. HICON hIcon = (HICON)::LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDR_MAINFRAME), IMAGE_ICON,::GetSystemMetrics(SM_CXICON),::GetSystemMetrics(SM_CYICON),LR_DEFAULTCOLOR); SetIcon(hIcon,TRUE); HICON hIconSmall = (HICON)::LoadImage(_Module.GetResourceInstance(),MAKEINTRESOURCE(IDR_MAINFRAME), IMAGE_ICON,::GetSystemMetrics(SM_CXSMICON),::GetSystemMetrics(SM_CYSMICON),LR_DEFAULTCOLOR); SetIcon(hIconSmall,FALSE); // Register object for message filtering and idle updates. CMessageLoop *pLoop = _Module.GetMessageLoop(); ATLASSERT(pLoop != NULL); pLoop->AddMessageFilter(this); pLoop->AddIdleHandler(this); UIAddChildWindowContainer(m_hWnd); // Setup controls. ::SendMessage(GetDlgItem(IDC_REFEDIT),EM_SETLIMITTEXT,MAX_PATH - 1,0); ::EnableWindow(GetDlgItem(IDC_EXPORTBUTTON),FALSE); m_TransList = GetDlgItem(IDC_TRANSLIST); return TRUE; } LRESULT CMainDlg::OnDropFiles(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled) { HDROP hDrop = (HDROP)wParam; POINT ptDrop; TCHAR szFullName[MAX_PATH]; if (DragQueryPoint(hDrop,&ptDrop) > 0) { unsigned int uiNumFiles = DragQueryFile(hDrop,0xFFFFFFFF,NULL,NULL); for (unsigned int i = 0; i < uiNumFiles; i++) { if (DragQueryFile(hDrop,i,szFullName,MAX_PATH - 1)) m_TransList.AddString(szFullName); } } DragFinish(hDrop); bHandled = false; return 0; } bool CMainDlg::AnalyzeTranslation(const TCHAR *szFileName,CXmlProcessor *pXml) { ::EnableWindow(GetDlgItem(IDC_EXPORTBUTTON),FALSE); TCHAR szRefFile[MAX_PATH]; GetDlgItemText(IDC_REFEDIT,szRefFile,MAX_PATH - 1); CLngAnalyzer RefFile(szRefFile); CLngAnalyzer LangFile(szFileName); if (RefFile.Load() != LNGRES_OK) return false; if (LangFile.Load() != LNGRES_OK) return false; // Add some translation information. pXml->AddElement(_T("Header"),_T(""),true); if (LangFile.EnterSection(_T("translation"))) { TCHAR *szStrValue; // Author. if (LangFile.GetValuePtr(1,szStrValue)) pXml->AddElement(_T("Author"),szStrValue); else pXml->AddElement(_T("Author"),_T("Unknown")); // Date. if (LangFile.GetValuePtr(2,szStrValue)) pXml->AddElement(_T("Date"),szStrValue); else pXml->AddElement(_T("Date"),_T("Unknown")); // Version. if (LangFile.GetValuePtr(3,szStrValue)) pXml->AddElement(_T("Version"),szStrValue); else pXml->AddElement(_T("Version"),_T("Unknown")); // Help. if (LangFile.GetValuePtr(4,szStrValue)) pXml->AddElement(_T("Help"),_T("Yes")); else pXml->AddElement(_T("Help"),_T("No")); } else { pXml->AddElement(_T("Author"),_T("Unknown")); pXml->AddElement(_T("Version"),_T("Unknown")); pXml->AddElement(_T("Date"),_T("Unknown")); pXml->AddElement(_T("Help"),_T("Unknown")); } // Ignore the values in the translation section. unsigned int uiRefTransCount = 0; CLngSection *pTempSection = RefFile.GetSection(_T("translation")); if (pTempSection != NULL) uiRefTransCount = (unsigned int)pTempSection->m_Values.size(); unsigned int uiLangTransCount = 0; pTempSection = LangFile.GetSection(_T("translation")); if (pTempSection != NULL) uiLangTransCount = (unsigned int)pTempSection->m_Values.size(); pXml->AddElement(_T("SectionRatio"),(double)LangFile.GetNumSections()/RefFile.GetNumSections()); pXml->AddElement(_T("ValueRatio"),(double)(LangFile.GetNumValues() - uiLangTransCount)/(RefFile.GetNumValues() - uiRefTransCount)); pXml->LeaveElement(); pXml->AddElement(_T("Missing"),_T(""),true); // Perform the comparission. TCHAR szBuffer[32]; unsigned int uiSectionCount = 0; for (unsigned int i = 0; i < RefFile.GetNumSections(); i++) { CLngSection *pRefSection = RefFile.GetSection(i); if (pRefSection == NULL) return false; // Skip the [translation] section. if (!lstrcmp(pRefSection->m_szName,_T("translation"))) continue; CLngSection *pLangSection = LangFile.GetSection(pRefSection->m_szName); if (pLangSection == NULL) { lsprintf(szBuffer,_T("Item%d"),uiSectionCount++); pXml->AddElement(szBuffer,_T(""),true); pXml->AddElementAttr(_T("name"),pRefSection->m_szName); for (unsigned int j = 0; j < pRefSection->m_Values.size(); j++) { lsprintf(szBuffer,_T("Item%d"),j); pXml->AddElement(szBuffer,pRefSection->m_Values[j]->m_szValue,true); pXml->AddElementAttr(_T("name"),(long)pRefSection->m_Values[j]->ulName); pXml->LeaveElement(); } pXml->LeaveElement(); } else { bool bAddSection = false; unsigned int uiValueCount = 0; // Compare the section values. for (unsigned int j = 0; j < pRefSection->m_Values.size(); j++) { if (!LangFile.SectionHasValue(pLangSection,pRefSection->m_Values[j]->ulName)) { // Add a new section if it hasn't already been added. if (!bAddSection) { lsprintf(szBuffer,_T("Item%d"),uiSectionCount++); pXml->AddElement(szBuffer,_T(""),true); pXml->AddElementAttr(_T("name"),pRefSection->m_szName); bAddSection = true; } lsprintf(szBuffer,_T("Item%d"),uiValueCount++); pXml->AddElement(szBuffer,pRefSection->m_Values[j]->m_szValue,true); pXml->AddElementAttr(_T("name"),(long)pRefSection->m_Values[j]->ulName); pXml->LeaveElement(); } } // Don't forget to leave any entered sections. if (bAddSection) pXml->LeaveElement(); } } pXml->LeaveElement(); return true; } LRESULT CMainDlg::OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { for (int i = 0; i < m_TransList.GetCount(); i++) { TCHAR szTransFileName[MAX_PATH]; m_TransList.GetText(i,szTransFileName); // Analyze the current translation. CXmlProcessor Xml(CXmlProcessor::MODE_HTML); Xml.AddElement(_T("InfraRecorder"),_T(""),true); Xml.AddElement(_T("Translation"),_T(""),true); AnalyzeTranslation(szTransFileName,&Xml); Xml.LeaveElement(); Xml.LeaveElement(); // Calculate new file name. ExtractFileName(szTransFileName); ChangeFileExt(szTransFileName,_T(".xml")); szTransFileName[0] = towlower(szTransFileName[0]); TCHAR szFileName[MAX_PATH]; ::GetModuleFileName(NULL,szFileName,MAX_PATH - 1); ExtractFilePath(szFileName); lstrcat(szFileName,szTransFileName); // Save the Xml document. Xml.Save(szFileName); } return 0; } LRESULT CMainDlg::OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { CloseDialog(wID); return 0; } LRESULT CMainDlg::OnClickedBrowseButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { WTL::CFileDialog FileDialog(true,0,0,OFN_FILEMUSTEXIST | OFN_EXPLORER, _T("Infra Recorder Languages (*.irl)\0*.irl\0\0"),m_hWnd); if (FileDialog.DoModal() == IDOK) SetDlgItemText(IDC_REFEDIT,FileDialog.m_szFileName); return 0; } LRESULT CMainDlg::OnClickedTransAddButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { WTL::CFileDialog FileDialog(true,0,0,OFN_FILEMUSTEXIST | OFN_EXPLORER, _T("Infra Recorder Languages (*.irl)\0*.irl\0\0"),m_hWnd); if (FileDialog.DoModal() == IDOK) m_TransList.AddString(FileDialog.m_szFileName); return 0; } LRESULT CMainDlg::OnClickedTransRemoveButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { if (m_TransList.GetCount() > 0 && m_TransList.GetCurSel() >= 0) m_TransList.DeleteString(m_TransList.GetCurSel()); return 0; } LRESULT CMainDlg::OnClickedTransClearButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled) { m_TransList.ResetContent(); return 0; } ================================================ FILE: src/tools/translationtool/main_dlg.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once #include class CMainDlg : public CDialogImpl,public CUpdateUI, public CMessageFilter,public CIdleHandler,public CDialogResize { private: CListBox m_TransList; bool AnalyzeTranslation(const TCHAR *szFileName,CXmlProcessor *pXml); public: enum { IDD = IDD_MAINDLG }; void CloseDialog(int iVal); virtual BOOL PreTranslateMessage(MSG *pMsg); virtual BOOL OnIdle(); BEGIN_UPDATE_UI_MAP(CMainDlg) END_UPDATE_UI_MAP() BEGIN_DLGRESIZE_MAP(CMainDlg) DLGRESIZE_CONTROL(IDOK,DLSZ_MOVE_X) DLGRESIZE_CONTROL(IDCANCEL,DLSZ_MOVE_X) DLGRESIZE_CONTROL(IDC_REFBUTTON,DLSZ_MOVE_X) DLGRESIZE_CONTROL(IDC_TRANSADDBUTTON,DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_TRANSREMOVEBUTTON,DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_TRANSCLEARBUTTON,DLSZ_MOVE_Y) DLGRESIZE_CONTROL(IDC_REFEDIT,DLSZ_SIZE_X) DLGRESIZE_CONTROL(IDC_TRANSLIST,DLSZ_SIZE_X | DLSZ_SIZE_Y) END_DLGRESIZE_MAP() BEGIN_MSG_MAP(CMainDlg) MESSAGE_HANDLER(WM_INITDIALOG,OnInitDialog) MESSAGE_HANDLER(WM_DROPFILES,OnDropFiles) COMMAND_ID_HANDLER(IDOK,OnOK) COMMAND_ID_HANDLER(IDCANCEL,OnCancel) COMMAND_HANDLER(IDC_REFBUTTON,BN_CLICKED,OnClickedBrowseButton) COMMAND_HANDLER(IDC_TRANSADDBUTTON,BN_CLICKED,OnClickedTransAddButton) COMMAND_HANDLER(IDC_TRANSREMOVEBUTTON,BN_CLICKED,OnClickedTransRemoveButton) COMMAND_HANDLER(IDC_TRANSCLEARBUTTON,BN_CLICKED,OnClickedTransClearButton) CHAIN_MSG_MAP(CDialogResize) END_MSG_MAP() LRESULT OnInitDialog(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnDropFiles(UINT uMsg,WPARAM wParam,LPARAM lParam,BOOL &bHandled); LRESULT OnOK(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnCancel(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnClickedBrowseButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnClickedTransAddButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnClickedTransRemoveButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); LRESULT OnClickedTransClearButton(WORD wNotifyCode,WORD wID,HWND hWndCtl,BOOL &bHandled); }; ================================================ FILE: src/tools/translationtool/resource.h ================================================ //{{NO_DEPENDENCIES}} // Microsoft Visual C++ generated include file. // Used by TranslationTool.rc // #define IDR_MAINFRAME 128 #define IDD_MAINDLG 129 #define IDC_REFSTATIC 1001 #define IDC_REFEDIT 1002 #define IDC_REFBUTTON 1005 #define IDC_EXPORTBUTTON 1010 #define IDC_TRANSSTATIC 1011 #define IDC_TRANSLIST 1012 #define IDC_TRANSADDBUTTON 1013 #define IDC_TRANSREMOVEBUTTON 1014 #define IDC_TRANSCLEARBUTTON 1015 // Next default values for new objects // #ifdef APSTUDIO_INVOKED #ifndef APSTUDIO_READONLY_SYMBOLS #define _APS_NEXT_RESOURCE_VALUE 201 #define _APS_NEXT_COMMAND_VALUE 32772 #define _APS_NEXT_CONTROL_VALUE 1016 #define _APS_NEXT_SYMED_VALUE 101 #endif #endif ================================================ FILE: src/tools/translationtool/stdafx.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #if (_ATL_VER < 0x0700) #include #endif //(_ATL_VER < 0x0700) ================================================ FILE: src/tools/translationtool/stdafx.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #pragma once // Change these values to use different versions. #define WINVER 0x0400 //#define _WIN32_WINNT 0x0400 #define _WIN32_IE 0x0400 #define _RICHEDIT_VER 0x0100 #include #include extern CAppModule _Module; #include #include #include #include #include "../../app/atl_compat.hh" // Manifest. #if defined _M_IX86 #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='x86' publicKeyToken='6595b64144ccf1df' language='*'\"") #elif defined _M_IA64 #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='ia64' publicKeyToken='6595b64144ccf1df' language='*'\"") #elif defined _M_X64 #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='amd64' publicKeyToken='6595b64144ccf1df' language='*'\"") #else #pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='*' publicKeyToken='6595b64144ccf1df' language='*'\"") #endif ================================================ FILE: src/tools/translationtool/translationtool.cc ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include "stdafx.hh" #include "resource.h" #include "main_dlg.hh" CAppModule _Module; int Run(LPTSTR lpstrCmdLine = NULL,int nCmdShow = SW_SHOWDEFAULT) { CMessageLoop MainLoop; _Module.AddMessageLoop(&MainLoop); CMainDlg MainDlg; if (MainDlg.Create(NULL) == NULL) { ATLTRACE(_T("Main dialog creation failed!\n")); return 0; } MainDlg.ShowWindow(nCmdShow); int nRet = MainLoop.Run(); _Module.RemoveMessageLoop(); return nRet; } int WINAPI _tWinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance,LPTSTR lpstrCmdLine,int nCmdShow) { HRESULT hRes = ::CoInitialize(NULL); // If you are running on NT 4.0 or higher you can use the following call instead to // make the EXE free threaded. This means that calls come in on a random RPC thread. //HRESULT hRes = ::CoInitializeEx(NULL, COINIT_MULTITHREADED); ATLASSERT(SUCCEEDED(hRes)); // This resolves ATL window thunking problem when Microsoft Layer for Unicode (MSLU) is used. ::DefWindowProc(NULL,0,0,0L); AtlInitCommonControls(ICC_BAR_CLASSES); // Add flags to support other controls. hRes = _Module.Init(NULL,hInstance); ATLASSERT(SUCCEEDED(hRes)); int nRet = Run(lpstrCmdLine,nCmdShow); _Module.Term(); ::CoUninitialize(); return nRet; } ================================================ FILE: src/tools/translationtool/translationtool.hh ================================================ /* * InfraRecorder - CD/DVD burning software * Copyright (C) 2006-2012 Christian Kindahl * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ ================================================ FILE: src/tools/translationtool/translationtool.rc ================================================ // Microsoft Visual C++ generated resource script. // #include "resource.h" #define APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 2 resource. // #include "atlres.h" ///////////////////////////////////////////////////////////////////////////// #undef APSTUDIO_READONLY_SYMBOLS ///////////////////////////////////////////////////////////////////////////// // English (U.S.) resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) #ifdef _WIN32 LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US #pragma code_page(1252) #endif //_WIN32 #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 1 TEXTINCLUDE BEGIN "resource.h\0" END 2 TEXTINCLUDE BEGIN "#include ""atlres.h""\r\n" "\0" END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Icon // // Icon with lowest ID value placed first to ensure application icon // remains consistent on all systems. IDR_MAINFRAME ICON "resources\\icon-main.ico" ///////////////////////////////////////////////////////////////////////////// // // Dialog // IDD_MAINDLG DIALOGEX 0, 0, 322, 116 STYLE DS_SETFONT | WS_MINIMIZEBOX | WS_MAXIMIZEBOX | WS_POPUP | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME CAPTION "TranslationTool" FONT 8, "MS Sans Serif", 0, 0, 0x0 BEGIN DEFPUSHBUTTON "Analyze",IDOK,265,7,50,14 PUSHBUTTON "Exit",IDCANCEL,265,24,50,14 LTEXT "Reference file:",IDC_REFSTATIC,7,9,47,8 EDITTEXT IDC_REFEDIT,60,7,173,13,ES_AUTOHSCROLL PUSHBUTTON "...",IDC_REFBUTTON,238,7,14,13 LTEXT "Translations:",IDC_TRANSSTATIC,7,25,41,8 LISTBOX IDC_TRANSLIST,60,23,192,69,LBS_SORT | LBS_NOINTEGRALHEIGHT | WS_VSCROLL | WS_TABSTOP,WS_EX_ACCEPTFILES PUSHBUTTON "Add",IDC_TRANSADDBUTTON,60,95,33,14 PUSHBUTTON "Remove",IDC_TRANSREMOVEBUTTON,97,95,33,14 PUSHBUTTON "Clear",IDC_TRANSCLEARBUTTON,134,95,33,14 END ///////////////////////////////////////////////////////////////////////////// // // DESIGNINFO // #ifdef APSTUDIO_INVOKED GUIDELINES DESIGNINFO BEGIN IDD_MAINDLG, DIALOG BEGIN LEFTMARGIN, 7 RIGHTMARGIN, 315 TOPMARGIN, 7 BOTTOMMARGIN, 109 END END #endif // APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Accelerator // IDR_MAINFRAME ACCELERATORS BEGIN "N", ID_FILE_NEW, VIRTKEY, CONTROL "O", ID_FILE_OPEN, VIRTKEY, CONTROL "S", ID_FILE_SAVE, VIRTKEY, CONTROL "P", ID_FILE_PRINT, VIRTKEY, CONTROL "Z", ID_EDIT_UNDO, VIRTKEY, CONTROL "X", ID_EDIT_CUT, VIRTKEY, CONTROL "C", ID_EDIT_COPY, VIRTKEY, CONTROL "V", ID_EDIT_PASTE, VIRTKEY, CONTROL VK_BACK, ID_EDIT_UNDO, VIRTKEY, ALT VK_DELETE, ID_EDIT_CUT, VIRTKEY, SHIFT VK_INSERT, ID_EDIT_COPY, VIRTKEY, CONTROL VK_INSERT, ID_EDIT_PASTE, VIRTKEY, SHIFT VK_F6, ID_NEXT_PANE, VIRTKEY VK_F6, ID_PREV_PANE, VIRTKEY, SHIFT END ///////////////////////////////////////////////////////////////////////////// // // Version // VS_VERSION_INFO VERSIONINFO FILEVERSION 1,0,0,1 PRODUCTVERSION 1,0,0,1 FILEFLAGSMASK 0x3fL #ifdef _DEBUG FILEFLAGS 0x1L #else FILEFLAGS 0x0L #endif FILEOS 0x4L FILETYPE 0x2L FILESUBTYPE 0x0L BEGIN BLOCK "StringFileInfo" BEGIN BLOCK "040904b0" BEGIN VALUE "FileDescription", "InfraRecorder Translation Tool" VALUE "FileVersion", "1.0.0.1" VALUE "InternalName", "translationtool" VALUE "LegalCopyright", "Copyright 2006-2010 Christian Kindahl" VALUE "OriginalFilename", "translationtool.exe" VALUE "ProductName", "InfraRecorder Translation Tool" VALUE "ProductVersion", "1.0.0.1" END END BLOCK "VarFileInfo" BEGIN VALUE "Translation", 0x409, 1200 END END ///////////////////////////////////////////////////////////////////////////// // // String Table // STRINGTABLE BEGIN IDR_MAINFRAME "TranslationTool" END STRINGTABLE BEGIN ID_FILE_NEW "Create a new document\nNew" ID_FILE_OPEN "Open an existing document\nOpen" ID_FILE_CLOSE "Close the active document\nClose" ID_FILE_SAVE "Save the active document\nSave" ID_FILE_SAVE_AS "Save the active document with a new name\nSave As" ID_FILE_PAGE_SETUP "Change the printing options\nPage Setup" ID_FILE_PRINT_SETUP "Change the printer and printing options\nPrint Setup" ID_FILE_PRINT "Print the active document\nPrint" ID_FILE_PRINT_PREVIEW "Display full pages\nPrint Preview" END STRINGTABLE BEGIN ID_APP_ABOUT "Display program information, version number and copyright\nAbout" ID_APP_EXIT "Quit the application; prompts to save documents\nExit" END STRINGTABLE BEGIN ID_NEXT_PANE "Switch to the next window pane\nNext Pane" ID_PREV_PANE "Switch back to the previous window pane\nPrevious Pane" END STRINGTABLE BEGIN ID_WINDOW_NEW "Open another window for the active document\nNew Window" ID_WINDOW_ARRANGE "Arrange icons at the bottom of the window\nArrange Icons" ID_WINDOW_CASCADE "Arrange windows so they overlap\nCascade Windows" ID_WINDOW_TILE_HORZ "Arrange windows as non-overlapping tiles\nTile Windows" ID_WINDOW_TILE_VERT "Arrange windows as non-overlapping tiles\nTile Windows" ID_WINDOW_SPLIT "Split the active window into panes\nSplit" END STRINGTABLE BEGIN ID_EDIT_CLEAR "Erase the selection\nErase" ID_EDIT_CLEAR_ALL "Erase everything\nErase All" ID_EDIT_COPY "Copy the selection and put it on the Clipboard\nCopy" ID_EDIT_CUT "Cut the selection and put it on the Clipboard\nCut" ID_EDIT_FIND "Find the specified text\nFind" ID_EDIT_PASTE "Insert Clipboard contents\nPaste" ID_EDIT_REPEAT "Repeat the last action\nRepeat" ID_EDIT_REPLACE "Replace specific text with different text\nReplace" ID_EDIT_SELECT_ALL "Select the entire document\nSelect All" ID_EDIT_UNDO "Undo the last action\nUndo" ID_EDIT_REDO "Redo the previously undone action\nRedo" END STRINGTABLE BEGIN ATL_IDS_SCSIZE "Change the window size" ATL_IDS_SCMOVE "Change the window position" ATL_IDS_SCMINIMIZE "Reduce the window to an icon" ATL_IDS_SCMAXIMIZE "Enlarge the window to full size" ATL_IDS_SCNEXTWINDOW "Switch to the next document window" ATL_IDS_SCPREVWINDOW "Switch to the previous document window" ATL_IDS_SCCLOSE "Close the active window and prompts to save the documents" END STRINGTABLE BEGIN ATL_IDS_SCRESTORE "Restore the window to normal size" ATL_IDS_SCTASKLIST "Activate Task List" ATL_IDS_MDICHILD "Activate this window" END STRINGTABLE BEGIN ATL_IDS_IDLEMESSAGE "Ready" END STRINGTABLE BEGIN ATL_IDS_MRU_FILE "Open this document" END #endif // English (U.S.) resources ///////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////// // Swedish resources #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_SVE) #ifdef _WIN32 LANGUAGE LANG_SWEDISH, SUBLANG_DEFAULT #pragma code_page(1252) #endif //_WIN32 #ifdef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // TEXTINCLUDE // 3 TEXTINCLUDE BEGIN "\r\0" END #endif // APSTUDIO_INVOKED #endif // Swedish resources ///////////////////////////////////////////////////////////////////////////// #ifndef APSTUDIO_INVOKED ///////////////////////////////////////////////////////////////////////////// // // Generated from the TEXTINCLUDE 3 resource. // ///////////////////////////////////////////////////////////////////////////// #endif // not APSTUDIO_INVOKED ================================================ FILE: src/tools/translationtool/translationtool_vc08.vcproj ================================================ ================================================ FILE: src/tools/translationtool/translationtool_vc10.vcxproj ================================================  Debug Win32 Debug x64 Release Win32 Release x64 Template Win32 Template x64 translationtool {890C6C24-55F8-466B-91BE-221F6214C3B8} translationtool Application Unicode Application Unicode Application Application Unicode Application Unicode <_ProjectFileVersion>10.0.30319.1 $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ true $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false $(ProjectDir)..\..\..\bin\$(Platform)\$(Configuration)\ $(ProjectDir)..\..\..\obj\$(ProjectName)\$(Platform)\$(Configuration)\ false AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset AllRules.ruleset $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\lib64\;$(CKROOTDIR)\ckcore\lib64\;$(LibraryPath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\lib\;$(CKROOTDIR)\ckcore\lib\;$(LibraryPath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) $(CKCOREDIR)\include\;$(CKROOTDIR)\ckcore\include\;$(IncludePath) _DEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)translationtool.tlb translationtool.hh translationtool_i.c translationtool_p.c Disabled $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;_DEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 EditAndContinue _DEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) ckcored.lib;%(AdditionalDependencies) true Windows MachineX86 _DEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)translationtool.tlb translationtool.hh translationtool_i.c translationtool_p.c Disabled $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;_DEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) true EnableFastChecks MultiThreadedDebug Use Level3 ProgramDatabase _DEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) ckcored.lib;%(AdditionalDependencies) true Windows MachineX64 NDEBUG;%(PreprocessorDefinitions) false Win32 true $(IntDir)translationtool.tlb translationtool.hh translationtool_i.c translationtool_p.c $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;NDEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) Sync MultiThreaded Use Level3 NDEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) /NODEFAULTLIB:atlmincrt.lib %(AdditionalOptions) ckcore.lib;%(AdditionalDependencies) Windows MachineX86 NDEBUG;%(PreprocessorDefinitions) false X64 true $(IntDir)translationtool.tlb translationtool.hh translationtool_i.c translationtool_p.c $(ProjectDir)..\..\;%(AdditionalIncludeDirectories) WIN32;_WINDOWS;STRICT;NDEBUG;_CRT_SECURE_NO_WARNINGS;_CRT_NON_CONFORMING_SWPRINTFS;%(PreprocessorDefinitions) Sync MultiThreaded Use Level3 NDEBUG;%(PreprocessorDefinitions) 0x0409 $(IntDir);%(AdditionalIncludeDirectories) /NODEFAULTLIB:atlmincrt.lib %(AdditionalOptions) ckcore.lib;%(AdditionalDependencies) Windows MachineX64 stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh Create stdafx.hh stdafx.hh stdafx.hh stdafx.hh stdafx.hh {81ea1bb3-2ba0-4600-9081-2d2cb9203466} false ================================================ FILE: src/tools/translationtool/translationtool_vc10.vcxproj.filters ================================================  {7f135e9d-1a42-46d4-b255-985930f45d55} cpp;c;cxx;def;odl;idl;hpj;bat;asm {a6feaf20-fce1-48ec-bda2-3d15b4297a65} h;hpp;hxx;hm;inl;inc {09219bad-a1c3-4acb-b33c-67f59cf986d7} rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;jpg;jpeg;jpe;manifest Source Files Source Files Source Files Source Files Header Files Header Files Header Files Header Files Resource Files Header Files Resource Files