class UIC::Application

The `Application` represents the root of your UIC application, corresponding to a `.uia` file.

Attributes

metadata[R]

@return [UIC::MetaData] the metadata loaded for this application

Public Class Methods

new(metadata,uia_path=nil) click to toggle source

@param metadata [UIC::MetaData] the `MetaData` to use for this application. @param uia_path [String] path to a `.uia` file to load.

If omitted you will need to later set the `.file = ` for the
instance and then call {#load_from_file}.
# File lib/ruic/application.rb, line 16
def initialize(metadata,uia_path=nil)
        @assets   = {}
        @metadata = metadata
        self.file = uia_path
end

Public Instance Methods

/(path)
Alias for: at
[](asset_id_or_path) click to toggle source

Find an asset by `.uia` identifier or path to the asset. @example

main1 = app['#main']
main2 = app['MyMain.uip']
main3 = app.main_presentation
assert main1==main2 && main2==main3

@param asset_id_or_path [String] an idref like `“#status”` or a relative path to the asset like `“VehicleStatus.uip”` or `“scripts/Main.lua”`. @return [UIC::Application::Behavior] @return [UIC::Application::StateMachine] @return [UIC::Application::Presentation] @return [UIC::Application::RenderPlugin]

# File lib/ruic/application.rb, line 49
def [](asset_id_or_path)
        all = assets
        if asset_id_or_path.start_with?('#')
                id = asset_id_or_path[1..-1]
                all.find{ |asset| asset.id==id }
        else
                full_path = File.expand_path(asset_id_or_path,File.dirname(file))
                all.find{ |asset| asset.file==full_path }
        end
end
assets() click to toggle source

@return [Array] all assets referenced by the application. Ordered by the order they appear in the `.uia`.

# File lib/ruic/application.rb, line 116
def assets
        @assets.values.inject(:+)
end
at(path) click to toggle source

Find an element or asset in a presentation by scripting path. @example

# Four ways to find the same layer
layer1 = app.at "main:Scene.Layer"
layer2 = app/"main:Scene.Layer"
layer3 = app.main.at "Scene.Layer"
layer4 = app.main/"Scene.Layer"

assert layer1==layer2 && layer2==layer3 && layer3==layer4

@return [MetaData::AssetBase] The found asset, or `nil` if it cannot be found.

@see Presentation#at @see MetaData::AssetBase#at

# File lib/ruic/application.rb, line 200
def at(path)
        parts = path.split(':')
        preso = parts.length==2 ? self["##{parts.first}"] : main_presentation
        raise "Cannot find presentation for #{id}" unless preso
        preso.at(parts.last)
end
Also aliased as: /
behaviors() click to toggle source

@return [Array<UIC::Application::Behavior>] all behaviors referenced by the application.

# File lib/ruic/application.rb, line 165
def behaviors
        @assets['behavior'] ||= []
end
directory_files() click to toggle source

@return [Array<String>] absolute paths of all files present in the application directory (used or not).

# File lib/ruic/application.rb, line 110
def directory_files
        dir = File.dirname(file)
        Dir.chdir(dir){ Dir['**/*.*'] }.map{ |f| File.expand_path(f,dir) }
end
image_paths() click to toggle source

@return [Array<String>] array of all image paths used by the application (not just in subfolders).

# File lib/ruic/application.rb, line 155
def image_paths
        image_usage.keys
end
image_usage() click to toggle source

@return [Hash] a mapping of image paths to arrays of elements/assets that reference that image.

# File lib/ruic/application.rb, line 141
def image_usage
        # TODO: this returns the same asset multiple times, with no indication of which property is using it; should switch to Properties.
        Hash[
                (presentations + statemachines)
                        .map(&:image_usage)
                        .inject{ |h1,h2| h1.merge(h2){ |path,els1,els2| [*els1,*els2] } }
                        .sort_by do |path,assets|
                                parts = path.downcase.split '/'
                                [ parts.length, parts ]
                        end
        ].tap{ |h| h.extend(UIC::PresentableHash) }
end
inspect() click to toggle source
# File lib/ruic/application.rb, line 5
def inspect
        "<UIC::Application '#{File.basename(file)}'#{:' FILENOTFOUND' unless file_found?}>"
end
main()
Alias for: main_presentation
main_presentation() click to toggle source

@example

main = app.main
main = app.main_presentation # more-explicit alternative

@return [UIC::Application::Presentation] the main presentation rendered by the application.

# File lib/ruic/application.rb, line 124
def main_presentation
        initial_id = @doc.at('assets')['initial']
        presos = presentations
        presos.find{ |pres| pres.id==initial_id } || presos.first
end
Also aliased as: main
main_presentation=(presentation) click to toggle source

Change which presentation is rendered for the application. @param presentation [UIC::Application::Presentation] @return [UIC::Application::Presentation]

# File lib/ruic/application.rb, line 134
def main_presentation=(presentation)
        # TODO: set to Presentation or Application::Presentation
        # TODO: create a unique ID if none exists
        @doc.at('assets')['initial'] = presentation.id
end
missing_files() click to toggle source

Files referenced by the application but not present in the directory.

@return [Array<String>] absolute paths of files referenced but gone.

# File lib/ruic/application.rb, line 93
def missing_files
        (referenced_files - directory_files).sort
end
on_doc_loaded() click to toggle source

Loads the application from the file. If you pass the path to your `.uia` to {#initialize} then this method is called automatically.

@return [nil]

# File lib/ruic/application.rb, line 26
def on_doc_loaded
        @assets  = @doc.search('assets *').map do |el|
                case el.name
                        when 'behavior'     then UIC::Application::Behavior
                        when 'statemachine' then UIC::Application::StateMachine
                        when 'presentation' then UIC::Application::Presentation
                        when 'renderplugin' then UIC::Application::RenderPlugin
                end.new(self,el)
        end.group_by{ |asset| asset.el.name }
        nil
end
presentations() click to toggle source

@return [Array<UIC::Application::Presentation>] all presentations referenced by the application.

# File lib/ruic/application.rb, line 160
def presentations
        @assets['presentation'] ||= []
end
referenced_files() click to toggle source

@return [Array<String>] absolute paths of files referenced by the application.

# File lib/ruic/application.rb, line 98
def referenced_files
        # TODO: state machines can reference external scripts
        # TODO: behaviors can reference external scripts
        (
                [file] +
                assets.map{ |asset| absolute_path(asset.src) } +
                statemachines.flat_map(&:referenced_files) +
                presentations.flat_map(&:referenced_files)
        ).uniq
end
renderplugins() click to toggle source

@return [Array<UIC::Application::RenderPlugin>] all render plug-ins referenced by the application.

# File lib/ruic/application.rb, line 175
def renderplugins
        @assets['renderplugin'] ||= []
end
save_all!() click to toggle source

Save changes to this application and every asset to disk.

# File lib/ruic/application.rb, line 180
def save_all!
        save!
        presentations.each(&:save!)
        # TODO: enumerate other assets and save them
end
statemachines() click to toggle source

@return [Array<UIC::Application::StateMachine>] all state machines referenced by the application.

# File lib/ruic/application.rb, line 170
def statemachines
        @assets['statemachine'] ||= []
end
unused_files( hierarchy=false ) click to toggle source

Files in the application directory not used by the application.

@return [Array<String>] absolute paths of files in the directory not used by the application.

# File lib/ruic/application.rb, line 63
def unused_files( hierarchy=false )
        unused = (directory_files - referenced_files).sort
        if hierarchy
                root = File.dirname(file)
                UIC.tree_hierarchy(root) do |dir|
                        File.directory?(dir) ? Dir.chdir(dir){ Dir['*'].map{ |f| File.expand_path(f) } } : []
                end.map do |prefix,file|
                        if file
                                all = unused.select{ |path| path[/^#{file}/] }
                                unless all.empty?
                                        size = NiceBytes.nice_bytes(all.map{ |f| File.size(f) }.inject(:+))
                                        partial = file.sub(/^#{root}\//o,'')
                                        if File.directory?(file)
                                                "%s %s (%d files, %s)" % [prefix,partial,all.length,size]
                                        else
                                                "%s %s (%s)" % [prefix,partial,size]
                                        end
                                end
                        else
                                prefix
                        end
                end.compact.join("\n")
        else
                unused
        end
end