FilterFunction.java revision 65953da4636fbf5f0a24b8f5f2b5fa7d76ff13d9
1c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy/*
2c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * Copyright (C) 2011 The Android Open Source Project
3c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy *
4c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * Licensed under the Apache License, Version 2.0 (the "License");
5c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * you may not use this file except in compliance with the License.
6c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * You may obtain a copy of the License at
7c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy *
8c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy *      http://www.apache.org/licenses/LICENSE-2.0
9c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy *
10c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * Unless required by applicable law or agreed to in writing, software
11c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * distributed under the License is distributed on an "AS IS" BASIS,
12c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * See the License for the specific language governing permissions and
14c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * limitations under the License.
15c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy */
16c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
17c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
18c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guypackage android.filterfw.core;
19c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
20c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guyimport java.util.Map.Entry;
21c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
22c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy/**
23c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy * @hide
24a2341a9f6addcd79723965ec5b1a1c5ae0f8bd65Romain Guy */
25a2341a9f6addcd79723965ec5b1a1c5ae0f8bd65Romain Guypublic class FilterFunction {
26c9855a53edfac818dc68714557185977556f849dRomain Guy
27c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    private Filter mFilter;
28fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy    private FilterContext mFilterContext;
29c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    private boolean mFilterIsSetup = false;
30c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    private FrameHolderPort[] mResultHolders;
31c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
32c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    private class FrameHolderPort extends StreamPort {
33c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        public FrameHolderPort() {
34c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            super(null, "holder");
35c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        }
36c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    }
37fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy
386203f6c8147069976342be8f42add797a50f9557Romain Guy    public FilterFunction(FilterContext context, Filter filter) {
39fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy        mFilterContext = context;
40fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy        mFilter = filter;
41fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy    }
42c9855a53edfac818dc68714557185977556f849dRomain Guy
43fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy    public Frame execute(KeyValueMap inputMap) {
44fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy        int filterOutCount = mFilter.getNumberOfOutputs();
45c9855a53edfac818dc68714557185977556f849dRomain Guy
46fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy        // Sanity checks
47fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy        if (filterOutCount > 1) {
48fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy            throw new RuntimeException("Calling execute on filter " + mFilter + " with multiple "
49fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy                + "outputs! Use executeMulti() instead!");
50fb8b763f762ae21923c58d64caa729b012f40e05Romain Guy        }
51c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
526203f6c8147069976342be8f42add797a50f9557Romain Guy        // Setup filter
53c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        if (!mFilterIsSetup) {
54c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            connectFilterOutputs();
55c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            mFilterIsSetup = true;
56c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        }
57c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
58c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        // Make sure GL environment is active
59c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        boolean didActivateGLEnv = false;
60c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        GLEnvironment glEnv = mFilterContext.getGLEnvironment();
61c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        if (glEnv != null && !glEnv.isActive()) {
62c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            glEnv.activate();
63c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            didActivateGLEnv = true;
64c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        }
65c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
66c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        // Setup the inputs
67c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        for (Entry<String, Object> entry : inputMap.entrySet()) {
68c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            if (entry.getValue() instanceof Frame) {
69c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy                mFilter.pushInputFrame(entry.getKey(), (Frame)entry.getValue());
70c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            } else {
71c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy                mFilter.pushInputValue(entry.getKey(), entry.getValue());
72c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            }
73c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        }
74c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
75c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        // Process the filter
76c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        if (mFilter.getStatus() != Filter.STATUS_PROCESSING) {
77c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            mFilter.openOutputs();
78c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        }
79c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
80c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        mFilter.performProcess(mFilterContext);
81c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
82c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        // Create result handle
83c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        Frame result = null;
846203f6c8147069976342be8f42add797a50f9557Romain Guy        if (filterOutCount == 1 && mResultHolders[0].hasFrame()) {
856203f6c8147069976342be8f42add797a50f9557Romain Guy            result = mResultHolders[0].pullFrame();
86c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        }
87c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
88c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        // Deactivate GL environment if activated
89c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        if (didActivateGLEnv) {
90c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            glEnv.deactivate();
91c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        }
92c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
93c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        return result;
94c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    }
95c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
96c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    public Frame executeWithArgList(Object... inputs) {
97c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        return execute(KeyValueMap.fromKeyValues(inputs));
98c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    }
99c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
1006203f6c8147069976342be8f42add797a50f9557Romain Guy    public void close() {
1016203f6c8147069976342be8f42add797a50f9557Romain Guy        mFilter.performClose(mFilterContext);
102c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    }
1036203f6c8147069976342be8f42add797a50f9557Romain Guy
1046203f6c8147069976342be8f42add797a50f9557Romain Guy    public FilterContext getContext() {
105c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        return mFilterContext;
1066203f6c8147069976342be8f42add797a50f9557Romain Guy    }
1076203f6c8147069976342be8f42add797a50f9557Romain Guy
108fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy    public Filter getFilter() {
1096203f6c8147069976342be8f42add797a50f9557Romain Guy        return mFilter;
1106203f6c8147069976342be8f42add797a50f9557Romain Guy    }
111fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy
112fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy    public void setInputFrame(String input, Frame frame) {
113fe48f65922d4a3cc4aefe058cee5acec51504a20Romain Guy        mFilter.setInputFrame(input, frame);
114c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    }
115c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
116c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    public void setInputValue(String input, Object value) {
1176203f6c8147069976342be8f42add797a50f9557Romain Guy        mFilter.setInputValue(input, value);
1186203f6c8147069976342be8f42add797a50f9557Romain Guy    }
119c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
120c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    public void tearDown() {
121c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        mFilter.performTearDown(mFilterContext);
122c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        mFilter = null;
123c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    }
124c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
125c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    @Override
126c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    public String toString() {
127c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        return mFilter.getName();
128c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    }
129c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy
130c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    private void connectFilterOutputs() {
131c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        int  i = 0;
132c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        mResultHolders = new FrameHolderPort[mFilter.getNumberOfOutputs()];
133c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        for (OutputPort outputPort : mFilter.getOutputPorts()) {
134c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            mResultHolders[i] = new FrameHolderPort();
135c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            outputPort.connectTo(mResultHolders[i]);
136c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy            ++i;
137c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy        }
138c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy    }
139c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy}
140c0ac193b9415680f0a69e20a3f5f22d16f8053beRomain Guy